It is not clear exactly how, but after a period of switching grandmaster between two nodes, pDelay on a third node becomes invalid. It is certain, however that drift between local and grandmaster clocks causes pDelay to drift too and potentially become invalid.
Invalid pDelay is observed in update_path_delay. The value is initially negative, and then, after adding a correction to clamp invalid negative to valid zero, the value becomes too large, crossing the 800ns threshold.
Both negative and too large values correctly cause reset of asCapable. Specification is written such that we assume invalid value is caused by peer and wait for peer to "correct itself". We continue computing pDelay until it becomes valid again and set asCapable back.
To recover asCapable in this manner, neighborRateRatio needs to be implemented, correcting for drift of local and grandmaster clocks.
Without neighborRateRatio, we seem to get stuck with asCapable unset, discarding sync messages so not doing any PTP adjusting that would bring asCapable back.
The setup to demonstrate the issue is 2 endpoints and a switch (Extreme Networks, but MOTU or DSP4YOU should work too). Unmodified firmware, changing PTP priority on the switch at random intervals between 0 and 30 seconds. Time to failure only a few minutes. With negative pDelay clamping implemented as described above, allow a couple of hours.