Repository navigation
Expose Expat XML attack protection APIs #90949
Description
Activity
Quoting from #31397 (comment)
"""
XML_SetBillionLaughsAttackProtectionActivationThresholdXML_SetBillionLaughsAttackProtectionMaximumAmplification
I still hope that someone can make those two^^ accessible (with additional glue code) to the user on pyexpat level in CPython.
""" - Sebastian Pipping @hartwork- added3.11only security fixesonly security fixestype-featureA feature request or enhancementA feature request or enhancement
on Feb 18, 2022 First mention at https://bugs.python.org/issue44394#msg395642
FYI starting with Expat 2.7.2, there are two new API functions more related to both security and amplification:
- addedextension-modulesC modules in the Modules dirC modules in the Modules dir
on Sep 17, 2025 @hartwork I have a question on the API usage. It appears that we can only call those functions on parsers without parents. Do you suggest that we:
- provide a module-wide function which, for any parser object created by the user, the function will be called automatically for orphan parsers, or
- keep it a per-parser configuration?
Having it enabled everywhere seems fine to me, considering that otherwise users would need to know whether a parser has a parent or not, however, there is no way to detect this on our side to warn them properly (the structure is opaque).
I think the only way to get a parser with a parent is through
XML_ExternalEntityParserCreatenbut I don't really know if I'm entirely right here.Reacted by Sebastian PippingHello @picnixz, thanks for your interest! 👍
@hartwork I have a question on the API usage. It appears that we can only call those functions on parsers without parents.
Yes. It's a deliberate choice to disallow that, the alternative would have been to instead find the root parser and apply the change to the root parser. The latter could be considered misleading or convenient, depending on view.
Do you suggest that we:
-
provide a module-wide function which, for any parser object created by the user, the function will be called automatically for orphan parsers, or
-
keep it a per-parser configuration?
Definitely not module wide — two unrelated parsers can have different limit and threshold values at runtime —, the rest I may not fully understand. Can you help me understand the rest better, e.g. the orphan part of it?
Having it enabled everywhere seems fine to me, considering that otherwise users would need to know whether a parser has a parent or not, however, there is no way to detect this on our side to warn them properly (the structure is opaque).
I think you're right that a parser cannot be asked "do you have a parent?" currently. "Not easily" for sure, "not at all" probably.
I think the only way to get a parser with a parent is through
XML_ExternalEntityParserCreatenbut I don't really know if I'm entirely right here.That is correct, it's the only way.
I'm happy to discuss this more.
-
By orphan I meant without a parent parser. What I wanted to know was whether we should, upon parser creation, call these new functions internally with thresholds and factors being set globally but you already answered by "no" so it's good on my side.
Considering the failure can only happen when either the parser has a parent or the factor is invalid as a number, I'm going to simply remake those checks on Python's side so that I can raise appropriate exceptions (ideally I would have loved having a return code being returned by expat so that I know what exactly happened but it's also fine).
Reacted by Sebastian Pipping31 remaining items
- added a commit that references this issue
on Dec 17, 2025 - added a commit that references this issue
on Aug 4, 2026
Note: these values reflect the state of the issue at the time it was migrated and might not reflect the current state.
Show more details
GitHub fields:
bugs.python.org fields:
Linked PRs
hasattrwith Expat security methods #139800