Ломать ли совместимость в недокументированной области?
От: Michael7 Россия  
Дата: 11.11.10 09:17
Оценка: 40 (9) +1
Предположим есть некий давно присутствующий на рынке программный продукт, с API, которое использует огромное число разработчиков.

Причем некоторые из разработчиков используют это API не описанным в документации способом или даже прямо там запрещенном (не в юридическом смысле) и никаких проблем от этого до сих пор не возникало, потому что, де-факто, оно работало нужным образом, хотя и не позволенным документацией.

В один прекрасный момент разработчики чего-то там у себя переписали и внезапно недокументированное поведение функции из API изменилось, что поломало совместимость и привело к ошибкам в работе и возмущениям.

И вот кто тут прав?

Ситуация невымышленная. Недавно эта история приключилась в Linux.
Подробности можно узнать из этого обсуждения.

Вкратце произошло вот что.

Есть важнейшая системная библиотека glibc (ее разработчики работают в основном в RedHat), в которой содержится сишный рантайм. В ней есть функция memcpy, копирующая память и описанная в документации как:

MEMCPY(3) Linux Programmer's Manual MEMCPY(3)

NAME
memcpy — copy memory area

SYNOPSIS
#include <string.h>

void *memcpy(void *dest, const void *src, size_t n);

DESCRIPTION
The memcpy() function copies n bytes from memory area src to memory
area dest. The memory areas should not overlap. Use memmove(3) if the
memory areas do overlap.


Она копирует из одной области памяти в другую заданное число байт. Специально указывается, что источник и приемник не должны пересекаться, если пересекаются необходимо использовать вместо memcpy функцию memmove. При том такое описание было с весьма древних пор, минимум с 1993-ого года или вообще с самого начала.

Но де-факто, реализация memcpy в glibc позволяла спокойно копировать и пересекающиеся области памяти. И вот разработчики чего-то там оптимизировали для увеличения скорости копирования, после чего в случае пересекающихся областей памяти копироваться они стали неверно.

Это привело к неправильному воспроизведению звука в плагине Adobe Flash player и к сбоям в некоторых других менее известных программах.

Разработчики glibc закрыли сообщение об ошибке по причине, что это не ошибка. Дискуссия развернулась довольно серьезная. В ней даже отметился лично Линус Торвальдс, который отнюдь не считает, что в glibc были правы, и даже ехидно спрашивает, собираются ли они выпустить дистрибутив Fedora 14 с заведомо неработоспособным флеш плеером?

В принципе, ошибка не в glibc, а в прикладных программах и для исправления достаточно банально заменить memcpy(...) на memmove(...) и заново откомпилировать программу. Для OpenSource — это особо не проблема, но в Linux-e работают и проприетарные программы, которые производители могут и не спешить исправлять. Правда Линус предложил способ решить проблему путем использования своей реализации memcpy и подкладывании своей библиотеки для конкретной программы. Но это костыль.

Такая вот любопытная дилемма получается. С одной стороны как бы разработчик не обязан обеспечивать совместимость за пределами документированного поведения, с другой стороны, вроде и поломка чужих важных программ после такого не есть хорошо.
Re: Ломать ли совместимость в недокументированной области?
От: Aen Sidhe Россия Просто блог
Дата: 11.11.10 09:23
Оценка: +3
Здравствуйте, Michael7, Вы писали:

M>Такая вот любопытная дилемма получается. С одной стороны как бы разработчик не обязан обеспечивать совместимость за пределами документированного поведения, с другой стороны, вроде и поломка чужих важных программ после такого не есть хорошо.


Есть много денег, как у Майкрософта — лепи костыль для каждого кулхацкера (как, например, поддержка SimCity и прочего). Нет много денег, как обычно, следи, чтобы документированное работало как работало.

В целом, виноваты, кулхацкеры, использовавшие недокументированные фичи.
С уважением, Анатолий Попов.
ICQ: 995-908
Re: Ломать ли совместимость в недокументированной области?
От: DOOM Россия  
Дата: 11.11.10 09:25
Оценка: +13
Здравствуйте, Michael7, Вы писали:

M>Такая вот любопытная дилемма получается. С одной стороны как бы разработчик не обязан обеспечивать совместимость за пределами документированного поведения, с другой стороны, вроде и поломка чужих важных программ после такого не есть хорошо.


Моя имха, что разработчик здесь прав на все 100%. Если что-то они просят не делать, то это, в частности, и для того, чтобы у них в будущем было пространство для маневра.
Схожий пример — зарезервированные поля в протоколах. Их обычно очень много — и, если вдруг кто-то начнет их использовать, чтобы передавать какие-то свои данные, то ни к чему хорошему это не приведет — потому что рано или поздно авторы протокола найдут применение этим полям.


P.S. Указанная проблема решается путем использования предыдущей версии glibc для пострадавших программ — вполне себе способ, учитывая, что проприетарные программы итак в 90% случаев используют библиотеки с префиксом compat
Re: Ломать ли совместимость в недокументированной области?
От: Sshur Россия http://shurygin-sergey.livejournal.com
Дата: 11.11.10 09:36
Оценка: +3
Здравствуйте, Michael7, Вы писали:

M>Предположим есть некий давно присутствующий на рынке программный продукт, с API, которое использует огромное число разработчиков.


M>Причем некоторые из разработчиков используют это API не описанным в документации способом или даже прямо там запрещенном (не в юридическом смысле) и никаких проблем от этого до сих пор не возникало, потому что, де-факто, оно работало нужным образом, хотя и не позволенным документацией.




It depends, как говорится. Тут недавно в КУ пролетала история про Microsoft, которая при выпуске я так понимаю 95-й винды затачивала системные библиотеки под конкретные глючившие игрушки и приложения. Со стороны разработчиков, кажется неправильно в системные библиотеки вводить условия, что если пользователь запускает SimCity, то менеджер памяти работает по другому. А со стороны пользователей хорошо, что старые программы работают в новой системе.

Так что вопрос скорее маркетинговый. Конкретно про линукс я думаю, что удобство для программистов, привыкших использовать memcpy недокументированным образом может быть важнее, чем выигрыш нескольких процентов в производительности. Зависит опять же от количества программистов и количества процентов
Шурыгин Сергей

"Не следует преумножать сущности сверх необходимости" (с) Оккам
Re: Ломать ли совместимость в недокументированной области?
От: Мишень-сан  
Дата: 11.11.10 11:06
Оценка:
Здравствуйте, Michael7, Вы писали:

[skipped]

ИМХО, виноваты авторы прикладного ПО. Во всех доках по С API жирными буквами написано не использовать memcpy для пересекающихся регионов. В С/С++ такие штуки караются UB. Если разрабы флеш-плеера не изволють читать доку...
Хотя, конечно, это можно решить элементарно — сделать и memcpy и memmove с проверкой на пересечение регионов, и в зависимости от этого использовать безопасный или небезопасный метод. Сомневаюсь, что несколько лишних инструкций на проверке overlap сделают погоду.
Re: Ломать ли совместимость в недокументированной области?
От: vmpire Россия  
Дата: 11.11.10 11:41
Оценка: 3 (1)
Здравствуйте, Michael7, Вы писали:

M>Предположим есть некий давно присутствующий на рынке программный продукт, с API, которое использует огромное число разработчиков.


M>Причем некоторые из разработчиков используют это API не описанным в документации способом или даже прямо там запрещенном (не в юридическом смысле) и никаких проблем от этого до сих пор не возникало, потому что, де-факто, оно работало нужным образом, хотя и не позволенным документацией.


M>В один прекрасный момент разработчики чего-то там у себя переписали и внезапно недокументированное поведение функции из API изменилось, что поломало совместимость и привело к ошибкам в работе и возмущениям.


M>И вот кто тут прав?

Вот, к примеру, сбивают сосульки с крыши. Оградили тротуар и написали, "не ходить".
Много раз люди ходили и ничего. Но вот как-то сосулька прилетела кому-то на голову.
И вот кто тут прав?
Re: Ломать ли совместимость в недокументированной области?
От: Anton Batenev Россия https://github.com/abbat
Дата: 11.11.10 11:45
Оценка:
Здравствуйте, Michael7, Вы писали:

M> Такая вот любопытная дилемма получается. С одной стороны как бы разработчик не обязан обеспечивать совместимость за пределами документированного поведения, с другой стороны, вроде и поломка чужих важных программ после такого не есть хорошо.


ИМХО, разработчики glibc правы в квадрате. Во первых, они действуют в рамках документации, а во вторых, раковые опухоли нужно вырезать, тем более, что особых проблем с открытым кодом это не вызывает, а закрытый — сами себе злобные буратины.
avalon 1.0rc3 rev 365, zlib 1.2.3
Re: Ломать ли совместимость в недокументированной области?
От: mrTwister Россия  
Дата: 11.11.10 12:28
Оценка: +8 :))) :))) :))) :))) :)
Здравствуйте, Michael7, Вы писали:

M>Предположим есть некий давно присутствующий на рынке программный продукт, с API, которое использует огромное число разработчиков.


M>Причем некоторые из разработчиков используют это API не описанным в документации способом или даже прямо там запрещенном (не в юридическом смысле) и никаких проблем от этого до сих пор не возникало, потому что, де-факто, оно работало нужным образом, хотя и не позволенным документацией.


M>В один прекрасный момент разработчики чего-то там у себя переписали и внезапно недокументированное поведение функции из API изменилось, что поломало совместимость и привело к ошибкам в работе и возмущениям.


M>И вот кто тут прав?


Ответ известен. Если разработчики — это разработчики Linux, значит виноваты те, кто использовал недокументированные возможности, ибо ССЗБ. Если речь идет о Microsoft, то виноват Microsoft, ибо криворукие, не могут обеспечить обратную совместимость.
лэт ми спик фром май харт
Re: Ломать ли совместимость в недокументированной области?
От: IT Россия linq2db.com
Дата: 11.11.10 14:55
Оценка: +7 -14 :))) :))
Здравствуйте, Michael7, Вы писали:

Разработчики glibc не виноватые, они просто козлы. Всё что надо было сделать, чтобы избежать конфликта — это написать новую версию memcpy — memcpy2 или лучше fastmemcpy, и в своей либе перейти на неё, если им нужно.
Если нам не помогут, то мы тоже никого не пощадим.
Re[2]: Ломать ли совместимость в недокументированной области
От: Pzz Россия https://github.com/alexpevzner
Дата: 11.11.10 15:07
Оценка:
Здравствуйте, Мишень-сан, Вы писали:

МС>Хотя, конечно, это можно решить элементарно — сделать и memcpy и memmove с проверкой на пересечение регионов, и в зависимости от этого использовать безопасный или небезопасный метод. Сомневаюсь, что несколько лишних инструкций на проверке overlap сделают погоду.


Разница в memcpy и memmove как раз в этих нескольких инструкциях. В memmove они есть, а я memcpy их нет.
Re[2]: Ломать ли совместимость в недокументированной области
От: Pzz Россия https://github.com/alexpevzner
Дата: 11.11.10 15:09
Оценка: 1 (1) +1
Здравствуйте, IT, Вы писали:

IT>Разработчики glibc не виноватые, они просто козлы. Всё что надо было сделать, чтобы избежать конфликта — это написать новую версию memcpy — memcpy2 или лучше fastmemcpy, и в своей либе перейти на неё, если им нужно.


Представляете, каково это программировать под систему, в которой десяток версий memcpy, и такая же ситуация с другими функциями, причем никто не может внятно объяснить, за давностью лет, чем эти функции различаются?

Если бы разработчики glibc действовали по вашему рецепту, так бы оно и было.
Re[3]: Ломать ли совместимость в недокументированной области
От: IT Россия linq2db.com
Дата: 11.11.10 15:46
Оценка: +5
Здравствуйте, Pzz, Вы писали:

Pzz>Представляете, каково это программировать под систему, в которой десяток версий memcpy, и такая же ситуация с другими функциями, причем никто не может внятно объяснить, за давностью лет, чем эти функции различаются?


Представляете сколько софта использует эту функцию, а сколько софта использует софт, который использует эту функцию? Почему-то, если что-то в совместимости отваливается у MS, то они козлы, а glibs, сцука, д'Артаньяны, борющиеся против злобных кулхацкеров.

Pzz>Если бы разработчики glibc действовали по вашему рецепту, так бы оно и было.


Только не надо демагогии. Ситуация не та. Этой функции 200 лет в обед. Софт который её использует уже давно пережил своих разработчиков. Да и нет никаких десятков версий memcpy. Есть одна, с давно известным, хотя и местами не совсем документированным поведением. Никакие оптимизации не стоят тысяч поломанных из-за них программ. К тому же это не просто поломка из серии вылет с иключением. Это порча памяти! Последствия будут аукаться ещё 200 лет в самые неожиданные моменты.

Ладно, забираю слова обратно. Разработчики glibs не козлы. Они — дебилы. Наверняка это изменение сделал какой-нибудь школяр только вчера допущенный к телу.
Если нам не помогут, то мы тоже никого не пощадим.
Re[4]: Ломать ли совместимость в недокументированной области
От: Pzz Россия https://github.com/alexpevzner
Дата: 11.11.10 16:23
Оценка: +2
Здравствуйте, IT, Вы писали:

IT>Представляете сколько софта использует эту функцию, а сколько софта использует софт, который использует эту функцию? Почему-то, если что-то в совместимости отваливается у MS, то они козлы, а glibs, сцука, д'Артаньяны, борющиеся против злобных кулхацкеров.


А представляете, сколько есть недокументированных полезных свойств у разных функций, про которые авторы glibc даже не знают, но которыми кто-нибудь пользуется? Как вы предлагаете девелопить glibc, поддерживая полную совместимость со всеми этими полезными функциями?

Микрософт давно сдался, и просто ставит кучу версий рантайма, чтобы старые программы не ломались при апгрейде рантайма. Только не очень понятно, кто в этом старом рантайме фиксит критические уязвимости. Я подозреваю, что никто.

IT>Только не надо демагогии. Ситуация не та. Этой функции 200 лет в обед. Софт который её использует уже давно пережил своих разработчиков. Да и нет никаких десятков версий memcpy. Есть одна, с давно известным, хотя и местами не совсем документированным поведением. Никакие оптимизации не стоят тысяч поломанных из-за них программ. К тому же это не просто поломка из серии вылет с иключением. Это порча памяти! Последствия будут аукаться ещё 200 лет в самые неожиданные моменты.


Я, вообще-то, еще когда зеленым сосунком писал свою первую программу на Си, знал, что memcpy можно использовать для неперекрывающихся данных, а для перекрывающихся надо использовать memmove().

Вы предлагаете сделать из Си язык для дебилов, неспособных прочитать документацию. Это чудесно, но на чём тогда программировать недебилам, которые знают разницу между этими 2-мя функциями и для которых эта небольшая экономия может быть существенна?
Re[2]: Ломать ли совместимость в недокументированной области
От: rsn81 Россия http://rsn81.wordpress.com
Дата: 11.11.10 16:38
Оценка: 5 (2) +4
Здравствуйте, Sshur, Вы писали:

S>It depends, как говорится. Тут недавно в КУ пролетала история про Microsoft, которая при выпуске я так понимаю 95-й винды затачивала системные библиотеки под конкретные глючившие игрушки и приложения. Со стороны разработчиков, кажется неправильно в системные библиотеки вводить условия, что если пользователь запускает SimCity, то менеджер памяти работает по другому. А со стороны пользователей хорошо, что старые программы работают в новой системе.

Это описывал Джоэл Спольски в своей статье Как Microsoft проиграла битву за API.

"Взгляните с точки зрения покупателя. Вы купили программы X, Y и Z. Затем вы обновились до Windows XP. Теперь ваш компьютер внезапно зависает, и программа Z вообще не работает. Вы скажите своим друзьям: «Не обновляйтесь до Windows XP. Она внезапно зависает и не совместима с программой Z». Будете ли вы дебажить вашу систему, чтобы определить, что программа X причина зависаний, а программа Z не работает, потому что использует недокументированные сообщения Windows? Конечно нет. Вы вернете коробку с Windows XP и получите обратно деньги. (Вы купили программы X, Y и Z несколько месяцев назад. 30-дневный срок возврата уже для них не действует. Единственное, что вы можете вернуть, это Windows XP.)"

Я впервые услышал об этом от одного из разработчиков популярной игры SimCity, который поведал мне о критической ошибке в их программе: она использовала память сразу после ее освобождения. Главное табу, нарушение которого прощалось в DOS, но карается в Windows, где освобожденную память тут же стащит другое работающее приложение. Тестеры в команде разработки Windows протестировали множество популярных приложений, чтобы убедиться, что все работает без сбоев, но SymCity зависала. Они сообщили это разработчикам Windows, которые дизассемблировали SymCity, шаг за шагом в дебаггере найдя ошибку, и добавили специальный код, проверяющий наличие SymCity в памяти и запускающий распределитель памяти в специальном режиме, в котором SymCity разрешается использовать память после ее освобождения.


S>Так что вопрос скорее маркетинговый. Конкретно про линукс я думаю, что удобство для программистов, привыкших использовать memcpy недокументированным образом может быть важнее, чем выигрыш нескольких процентов в производительности. Зависит опять же от количества программистов и количества процентов

Общая мысль в том, что пользователям не нужны именно сами операционные системы, им нужны работающие программы. Отсюда следует, что ответственность разработчиков ОС совершенно иная, нежели ответственность разработчиков программ.
Re[5]: Ломать ли совместимость в недокументированной области
От: hardcase Пират http://nemerle.org
Дата: 11.11.10 16:49
Оценка:
Здравствуйте, Pzz, Вы писали:

Pzz>Вы предлагаете сделать из Си язык для дебилов, неспособных прочитать документацию. Это чудесно, но на чём тогда программировать недебилам, которые знают разницу между этими 2-мя функциями и для которых эта небольшая экономия может быть существенна?


Все это прекрасно и очень правильно при одном условии... Пишется новая программа.
Кто может гарантировать что каждую отдельно взятую старую программу писал не лопух?
/* иЗвиНите зА неРовнЫй поЧерК */
Re[6]: Ломать ли совместимость в недокументированной области
От: Pzz Россия https://github.com/alexpevzner
Дата: 11.11.10 16:56
Оценка: +2 :))
Здравствуйте, hardcase, Вы писали:

Pzz>>Вы предлагаете сделать из Си язык для дебилов, неспособных прочитать документацию. Это чудесно, но на чём тогда программировать недебилам, которые знают разницу между этими 2-мя функциями и для которых эта небольшая экономия может быть существенна?


H>Все это прекрасно и очень правильно при одном условии... Пишется новая программа.

H>Кто может гарантировать что каждую отдельно взятую старую программу писал не лопух?

Никто. А что делать-то? Си не предназначен для лопухов. Если сделать из Си язык для лопухов, подложив всюду соломки, то нелопухам будет не на чем программировать.
Re[3]: Ломать ли совместимость в недокументированной области
От: Mr.Cat  
Дата: 11.11.10 17:22
Оценка:
Здравствуйте, rsn81, Вы писали:
R>добавили специальный код, проверяющий наличие SymCity в памяти и запускающий распределитель памяти в специальном режиме, в котором SymCity разрешается использовать память после ее освобождения.
Не зная причин, обсуждать принятое решение бессмысленно, но идеологически правильным вариантом мог быть выпуск патча для SimCity и включение его в дистрибутив ОСи.
Re[7]: Ломать ли совместимость в недокументированной области
От: Pavel Dvorkin Россия  
Дата: 11.11.10 17:42
Оценка: +1
Здравствуйте, Pzz, Вы писали:

H>>Кто может гарантировать что каждую отдельно взятую старую программу писал не лопух?


Pzz>Никто. А что делать-то? Си не предназначен для лопухов. Если сделать из Си язык для лопухов, подложив всюду соломки, то нелопухам будет не на чем программировать.


Ты неправ. Если эта старая программа работала многие годы, то можно гарантировать, что писал ее не лопух. Программы, написанные на С лопухами, помирают в младенческом возрасте
With best regards
Pavel Dvorkin
Re[4]: Ломать ли совместимость в недокументированной области
От: gandjustas Россия http://blog.gandjustas.ru/
Дата: 11.11.10 18:08
Оценка: +2 -3
Здравствуйте, Mr.Cat, Вы писали:

MC>Здравствуйте, rsn81, Вы писали:

R>>добавили специальный код, проверяющий наличие SymCity в памяти и запускающий распределитель памяти в специальном режиме, в котором SymCity разрешается использовать память после ее освобождения.
MC>Не зная причин, обсуждать принятое решение бессмысленно, но идеологически правильным вариантом мог быть выпуск патча для SimCity и включение его в дистрибутив ОСи.
Нифига не правильным. Если разработчики SimCity (или другой программы) выпустят обновление? Или свой патч, который будет несвоместим?

Как раз патч в ОС, который сделали разработчики windows — лучшее решение. Сейчас база данных совместимости программ Windows содержит тысячи, таких патчей, для того чтобы программы работали. А вот разработчики glibc положили йух на такую совместимость.
Re[4]: Ломать ли совместимость в недокументированной области
От: rsn81 Россия http://rsn81.wordpress.com
Дата: 11.11.10 18:09
Оценка: +2
Здравствуйте, Mr.Cat, Вы писали:

MC>Не зная причин, обсуждать принятое решение бессмысленно, но идеологически правильным вариантом мог быть выпуск патча для SimCity и включение его в дистрибутив ОСи.

Идеалогически правильный вариант отсрочил бы выпуск ОС на неопределенное время, что вероятно привело бы в неопределенно громадным убыткам.
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.