[Date Prev][Date Next] [Thread Prev][Thread Next] [Date Index] [Thread Index]

Re: Как реализован "in place upgrade" в Дебиан? На чем основан и чем чревато?



On 2012.11.11 at 00:34:10 +0200, Oleksandr Gavenko wrote:

>   Packages can be upgraded in place, even in running systems.
> 
> Собственно понятие на "юзерском" уровне есть. Как бы обновление без
> перезаuрузки или остановки сторонних сервисов.
> 
> Естественно что такие действия "опасные". Например случаи:
> 
>  * Если разделяемая библиотека загружена в память несколькими процесами.
>  * Если программа из одного пакета обращается к файлу из другого пакета (-bin и
>    -data пакеты).

> К примеру, в Cygwin рекомендуют закрывать все Cygwin сервисы и программы. Если

Cygwin работает на файловой системе NTFS. Которая не позволяет удалять
файлы, открытые работающим процессом.

В Unix-подобных системах, в том числе и в Linux файловая система
работает по-другому. Ссылка на файл из каталога (т.н. hardlink) и
ссылка на файл из
открывшего его процесса фактически равноправны. На файл может
существовать сколько угодно ссылок, и он физически удаляется с диска
только если исчезла последняя ссылка на него.

Поэтому, если удалить разделяемую библиотеку обыкновенным системным
вызовом unlink(2), процессы, использующие эту библиотеку будут
продолжать её видеть.  А package manager или утилита install могут
прекрасно записать новую библиотеку на место старой.

И только при завершении последнего процесса, использюующего старую
библиотеку, она физически будет удалена с диска (inode помечен как
deleted).

Если внимательно следить да debian-системой в процессе апгрейда основной
системной библиотеки (glibc) то можно увидеть что при апгрейде иногда
производится перезапуск некоторого набора сервисов.

Это делается потому что glibc на самом деле не одна библиотека, а
несколько (всякие там подгружаемые модули libnss). И если апгрейд таков,
что процессы, подгрузившие старый libc.so не смогут при необходимости
работать с  новыми  libnss, которые им захочется подгрузить позже, 
при завершении апгрейда процессы перезапускают.

Кроме уже рассмотренного системного вызова unlink(2) есть еще вызов
rename(2).  Он отличается тем, что работает атоммарно. Поэтому если
записать файл на диск под именем something.tmp а потом удалить старый
something и переименовать something.tmp в something, время когда на
диске не существует корректного файла c именем something (либо старого, либо
нового) будет минимальным. 




Reply to: