Eugene Yavorsky
eugene_yavorsky@mail.ru
Озаботившись проблемой работы моего плагина в различных версиях ФАРа, от лени не стал изобретать велосипеды и попытался вставить готовую "козу" из упомянутой выше статьи ("Плагин для разных версий FAR Manager" FAR Group), однако код работал как-то странно. Написав по его просьбе тестовый плагин (по приведенному коду - после исправления опечаток) и протестировав его, получил следующие результаты.
Сборка плагина производилась с версиями plugin.hpp из поставки публичных бет:
А также с plugin.hpp от какой-то 6-й альфы, не помню где взятым:
Далее эти версии plugin.hpp будут мною для простоты нумероваться как 1701, 1702, 1704, 1705 и 1706.
Тестирование проводилось в следующих публичных версиях ФАРа:
И двух 6-х альфах:
Для ФАРов 1.60 и 1.65 поведение всех версий плагина не отличалось:
::Info.StructSize < sizeof(struct PluginStartupInfo)
и матерится при каждом вызове (т.е. при каждом F11, вызове меню настроек плагинов, смене языка и т.д.)Для ФАРов 1.701-1.706 build 1736
На основании логов проверено фунциклирование GetMinFARVersion(). По горизонтали всех таблиц - версия ФАРа, по вертикали - версия plugin.hpp
- ФАР не ругается на "плохую" версию плагина (а надо бы)
+ ФАР ругается на "плохую" версию плагина
. ФАР не ругается на "плохую" версию плагина - и не надо
| Версия plugin.hpp | 1701 | 1702 | 1703 | 1704 | 1705 | 1706 build 1658 | 1706 build 1736 |
|---|---|---|---|---|---|---|---|
| 1701 | . | . | . | . | . | . | . |
| 1702 | - | . | . | . | . | . | . |
| 1703 | - | - | . | . | . | . | . |
| 1704 | - | - | - | . | . | . | . |
| 1705 | - | - | - | + | . | . | . |
| 1706 | - | - | - | + | + | + | . |
При анализе логов для ФАРов 1701-1703 вообще нет свидетельств о вызове GetMinFARVersion().
Т.о., ФАР и GetMinFARVersion() ведет себя документированным и предполагаемым образом только в ФАРах 1704 и выше.
После титанических интеллектуальных усилий код был поправлен следующим образом:
// Ставим тут нужную нам версию
#define HPPVER "1.705"
BOOL bBadFAR = FALSE;
DWORD dwFARVERSION;
void WINAPI SetStartupInfo(struct PluginStartupInfo *PSInfo)
{
if(PSInfo->StructSize < sizeof(struct PluginStartupInfo))
{
memcpy(&Info,PSInfo,PSInfo->StructSize);
bBadFAR = TRUE;
}else{
Info = *PSInfo;
FSF = *PSInfo->FSF;
Info.FSF = &FSF;
Info.AdvControl(Info.ModuleNumber, ACTL_GETFARVERSION, &dwFARVERSION);
if(dwFARVERSION < FARMANAGERVERSION)
bBadFAR = TRUE;
}
if(bBadFAR)
Message("Этот плагин требует FAR Manager версии "HPPVER" и выше!");
}
int WINAPI GetMinFarVersion(void)
{
return FARMANAGERVERSION;
}
void WINAPI GetPluginInfo(struct PluginInfo *Info)
{
if(bBadFAR)
return;
// Далее пошла инициализация PluginInfo
}
После тестирования по той же программе получаем:
Для ФАРов 1.60-1.65:
::Info.StructSize < sizeof(struct PluginStartupInfo)
и устанавливает bBadFAR = TRUE и один раз материтсяДля ФАРов 1.701-1.706 build 1736
Обозначения:
+ФАР ругается на "плохую" версию плагина (что достигается корректной работой GetMinFarVersion())
#плагин ругается на "плохую" версию ФАРа (что достигается наличием в SetStartupInfo()):
Info.AdvControl(Info.ModuleNumber, ACTL_GETFARVERSION, &dwFARVERSION);
if(dwFARVERSION < FARMANAGERVERSION){
bBadFAR = TRUE;
Message("Этот плагин требует FAR Manager версии "HPPVER" и выше!");
}
При этом GetPluginInfo() в ответ на bBadFAR = TRUE сваливает без заполнения PluginInfo и плагин не светится в списке.
+ GetPluginInfo() заполняет PluginInfo, плагин в списке и работает.
| Версия plugin.hpp | 1701 | 1702 | 1703 | 1704 | 1705 | 1706 build 1658 | 1706 build 1736 |
|---|---|---|---|---|---|---|---|
| 1701 | . | . | . | . | . | . | . |
| 1702 | # | . | . | . | . | . | . |
| 1703 | # | # | . | . | . | . | . |
| 1704 | # | # | # | . | . | . | . |
| 1705 | # | # | # | + | . | . | . |
| 1706 | # | # | # | + | + | + | . |
Т.о., получаем необходимую и логичную функциональность для всех протестированных версий ФАРа и plugin.hpp.
Полные версии тестировочных плугинов (старого - "неправильного" и нового - "поправленного") и соответствующих логов есть на PlugRin`е и будут лежать еще тут.
15.05.2004
Внимание!
if(dwFARVERSION < FARMANAGERVERSION)".
Это связано с тем, как FAR хранит версию.
Необходимо сравнить старшую и младшую компоненты версии, например:
if (LOWORD(dwFARVERSION) < LOWORD(FARMANAGERVERSION) ||
(LOWORD(dwFARVERSION) == LOWORD(FARMANAGERVERSION) &&
HIWORD(dwFARVERSION) < HIWORD(FARMANAGERVERSION)))
{
bBadFAR = TRUE;
}