Open boesing opened 9 months ago
BTW, is this causing an infinite "loop" or infinite "recursion"?
I have to admit that I have no clue if and how there is a difference tbh.
The way I use "recursion" usually is that something is happening within the same class. This issue is actually passing a bunch of classes and methods which in the end leads to the same canCreate
method (in the has
trace) which then triggers the same process again:
$container->has('foo');
services
, aliases
and factories
for foo
foo
not found in services
, aliases
or factories
foo
$container->has('foo');
will start over No. 1So no clue if this is actually an infinite loop or infinite recursion.
I would implement somthing like this:
if (isset($this->pendingAbstractFactoryChecks[$name])) {
return false;
}
$this->pendingAbstractFactoryChecks[$name] = $name;
foreach ($this->abstractFactories as $abstractFactory) {
if ($abstractFactory->canCreate($this->creationContext, $name)) {
unset($this->pendingAbstractFactoryChecks[$name]);
return true;
}
}
$resolvedName = $this->aliases[$name] ?? $name;
if ($resolvedName !== $name) {
if ($this->abstractFactoryCanCreate($resolvedName)) {
unset($this->pendingAbstractFactoryChecks[$name]);
return true;
}
}
unset($this->pendingAbstractFactoryChecks[$name]);
return false;
But I guess that the problem might be that we have to keep track of which abstract factory is currently being checked and just skip that abstract factory which was called lately so that all but the current one is being checked. So the code above might be too "dumb".
I have to admit that I have no clue if and how there is a difference tbh.
infinite loop runs forever. infinite recursion usually leads to a segfault/crash. an infinite loop would be much worse, right now.
I rephrased the issue and replaced loop
with recursion
. Thx for clarification.
Bug Report
Summary
There is a lack of infinite recursion detection for both
get
andhas
when it comes to abstract factories.Ref: https://github.com/laminas/laminas-cache/issues/284
Current behavior
When checking a service via
has
in factories (one abstract factory has to be involved) or receiving a service viaget
, an infinite recursion along with an application crash is the result.$container->has('foo');
services
,aliases
andfactories
forfoo
foo
not found inservices
,aliases
orfactories
foo
$container->has('foo');
will start over No. 1How to reproduce
Expected behavior
Infinite recursions are prevented from abstract factories.