Хорошо, после того, как еще некоторые думали, что я думаю, что у меня есть ясное решение.
Критическое понимание то, что, если каждая ссылка, которая является частью пути, решает к чему-то, затем вся твердость пути. Или наоборот, если путь не решает затем, должна быть определенная символьная ссылка, которая требует пересечения, которое не решает.
При размышлении об этой проблеме ранее я использовал алгоритм, который пересек элементы пути, начинающего с корня, и когда это встретилось с символьной ссылкой, это заменило тот элемент пути содержанием символьной ссылки и затем продолжило пересекать. Так как этот подход не помнит, какая символьная ссылка он в настоящее время разрешает, что не может обнаружить, когда это находится в цикле неразрешения.
Если алгоритм отслеживает, которой символьной ссылки он в настоящее время решает (или который символьные ссылки в случае рекурсивных ссылок), он может обнаружить, если он пытается разрешить ссылку снова рекурсивно, которую это все еще занято, разрешая.
Алгоритм:
initialize `location` to the current working directory
initialize `link_contents` to the path we want to resolve
initialize `active_symlinks` to the empty set
def resolve_symlink(location, link_contents, active_symlinks) :
loop forever:
next_location = location / [first element of link_contents]
see if next_location is a symlink.
if so:
if next_location in active_symlinks: abort, we have a loop
location = resolve_symlink(location, readlink(next_location), active_symlinks ∪ {next_location})
else:
location = next_location
strip first element of link_contents
if link_contents is empty:
return location
править:
У меня есть рабочая реализация этого в Python в https://bitbucket.org/JanKanis/python-inotify/src/853ed903e870cbfa283e6ce7a5e41aeffe16d4e7/inotify/pathresolver.py? at=pathwatcher.