Open
Fix CVE-2026-12570: unbounded memory allocation in HDF5 dataset loading #47
Fix CVE-2026-12570: unbounded memory allocation in HDF5 dataset loading #47
Open
nebdAdd on Aug 13
Total: 2 files changed+103-1
@@ -0,0 +1,95 @@
1+From 4933ea4a5b3fcc24ceacdc276f5bb5dfbd06756c Mon Sep 17 00:00:00 2001
2+From: Ziyu Lin <104151270+LinZiyuu@users.noreply.github.com>
3+Date: Mon, 17 Aug 2026 14:49:19 +0800
4+Subject: [PATCH] Fix CVE-2026-12570: guard against HDF5 shape/decompression
5+ bomb
6+ 
7+In keras 2.12.0, H5IOStore.get() returns an HDF5 group object whose
8+datasets are accessed directly by _load_own_variables via store[key].
9+A crafted .keras file can contain an HDF5 dataset that declares an
10+enormous shape (e.g. petabytes) while occupying only a few kilobytes
11+on disk (chunked + compressed + fill-value-only). When the dataset is
12+read into memory via v.assign(store[key]), h5py attempts to allocate
13+memory for the full declared shape, triggering an OOM condition.
14+ 
15+Add validate_h5_dataset to saving_lib.py and call it from
16+base_layer._load_own_variables before reading each dataset.
17+ 
18+Origin: https://github.com/keras-team/keras/commit/4933ea4a5b3fcc24ceacdc276f5bb5dfbd06756c
19+Issue: https://atomgit.com/src-openeuler/python-Keras/issues/31
20+---
21+ keras/engine/base_layer.py | 4 +++-
22+ keras/saving/saving_lib.py | 35 +++++++++++++++++++++++++++++++++++
23+ 2 files changed, 38 insertions(+), 1 deletion(-)
24+ 
25+diff --git a/keras/engine/base_layer.py b/keras/engine/base_layer.py
26+index 6d126b6..e1ad50e 100644
27+--- a/keras/engine/base_layer.py
28++++ b/keras/engine/base_layer.py
29+@@ -3518,7 +3518,9 @@ class Layer(tf.Module, version_utils.LayerVersionSelector):
30+ )
31+ for i, v in enumerate(all_vars):
32+ # TODO(rchao): check shapes and raise errors.
33+- v.assign(store[f"{i}"])
34++ val = store[f"{i}"]
35++ saving_lib.validate_h5_dataset(val, name=f"{i}")
36++ v.assign(val)
37+
38+
39+ class TensorFlowOpLayer(Layer):
40+diff --git a/keras/saving/saving_lib.py b/keras/saving/saving_lib.py
41+index 9e52ecf..f6ec9c9 100644
42+--- a/keras/saving/saving_lib.py
43++++ b/keras/saving/saving_lib.py
44+@@ -17,6 +17,7 @@
45+ import datetime
46+ import io
47+ import json
48++import math
49+ import os
50+ import re
51+ import tempfile
52+@@ -668,6 +669,40 @@ class NpzIOStore:
53+ self.f.close()
54+
55+
56++# Guard against HDF5 "shape bomb" datasets (CVE-2026-12570).
57++# A dataset can declare an enormous shape while storing almost nothing on disk
58++# (e.g. chunked + gzip-compressed with only a fill value), which forces a huge
59++# allocation when it is read into memory (CWE-789 / CWE-409). For datasets
60++# whose declared in-memory size is above this floor, we require it to stay
61++# within _H5_DATASET_MAX_EXPANSION of the bytes actually stored on disk.
62++_H5_DATASET_BOMB_FLOOR_BYTES = 1 << 32 # 4 GiB
63++_H5_DATASET_MAX_EXPANSION = 1000
64++
65++
66++def validate_h5_dataset(dataset, name="<unknown>"):
67++ """Validate that an HDF5 dataset is not a shape/decompression bomb.
68++
69++ Checks that the dataset's declared in-memory size is not
70++ disproportionately larger than the bytes actually stored on disk.
71++ """
72++ if h5py is None:
73++ return
74++ if not isinstance(dataset, h5py.Dataset):
75++ return
76++ declared_bytes = math.prod(dataset.shape) * dataset.dtype.itemsize
77++ stored_bytes = dataset.id.get_storage_size()
78++ if (
79++ declared_bytes > _H5_DATASET_BOMB_FLOOR_BYTES
80++ and declared_bytes > _H5_DATASET_MAX_EXPANSION * stored_bytes
81++ ):
82++ raise ValueError(
83++ f"Not allowed: H5 dataset '{name}' declares "
84++ f"{declared_bytes} bytes in memory but only "
85++ f"{stored_bytes} bytes are stored on disk; "
86++ "refusing to load a potential decompression/shape bomb."
87++ )
88++
89++
90+ def _get_temp_dir():
91+ temp_dir = tempfile.mkdtemp()
92+ testfile = tempfile.TemporaryFile(dir=temp_dir)
93+--
94+2.55.0
95+ 
@@ -1,7 +1,7 @@
1%global _empty_manifest_terminate_build 01%global _empty_manifest_terminate_build 0
2Name: python-Keras2Name: python-Keras
3Version: 2.12.03Version: 2.12.0
4-Release: 44+Release: 5
5Summary: Deep Learning for humans5Summary: Deep Learning for humans
6License: Apache-2.06License: Apache-2.0
7URL: https://github.com/keras-team/keras7URL: https://github.com/keras-team/keras
@@ -11,6 +11,7 @@ BuildArch: noarch
11Patch0: backport-CVE-2025-12058.patch11Patch0: backport-CVE-2025-12058.patch
12Patch1: backport-CVE-2026-12482.patch12Patch1: backport-CVE-2026-12482.patch
13Patch2: backport-CVE-2026-11816.patch13Patch2: backport-CVE-2026-11816.patch
14+Patch3: backport-CVE-2026-12570.patch
14 15 
15Requires: python3-numpy16Requires: python3-numpy
16Requires: python3-scipy17Requires: python3-scipy
@@ -100,6 +101,12 @@ mv %{buildroot}/doclist.lst .
100%{_docdir}/*101%{_docdir}/*
101 102 
102%changelog103%changelog
104+* Thu Aug 13 2026 shaojiansong <shaojiansong@kylinos.cn> - 2.12.0-5
105+- Type:CVE
106+- CVE:CVE-2026-12570
107+- SUG:NA
108+- DESC:Security fix: unbounded memory allocation in HDF5 dataset loading (shape/decompression bomb). Add validate_h5_dataset to guard against malicious .keras model files.
109+ 
103* Wed Jul 22 2026 lizhengde <lizhengde@xfusion.com> - 2.12.0-4110* Wed Jul 22 2026 lizhengde <lizhengde@xfusion.com> - 2.12.0-4
104- Type:CVE111- Type:CVE
105- CVE:CVE-2026-11816112- CVE:CVE-2026-11816