PDA

Просмотр полной версии : Глюки библиотеки SysLibCom



alex1963
15.01.2009, 18:07
Очень простая библиотека SysLibCom - всего-то буферизованный неструктурированный обмен с посл. интерфейсами, но сколько глюков :(

1) SysComOpen() при успешном открытии возвращает 0 вместо хэндла порта. А другим функциям надо давать номер порта вместо хендла. Да, об этом сказано в русской документации, но если пользователь заглянет в хелп или английскую документацию :( . Зачем такая несовместимость - ведь хендл по определению может быть чем угодно, в том числе и совпадать с номером порта, если разработчику так удобнее.

2) После открытия порт надо "запускать" - опять фирменная Овеновская особенность. А если SysComOpen() его сразу запускать будет - что страшного случится?

3) Если порт уже открыт, повторно он не открывается. Это естественно. Но неестественно то, что он не закрывается по RESET! Кстати, такой же эффект замечен и для сокетов. Для файлов еще не пробовал :). Господа, RESET - это УСТАНОВКА ВСЕГО ОБОРУДОВАНИЯ И ПО В НАЧАЛЬНОЕ СОСТОЯНИЕ! Сбрасывать ПЛК по питанию при отладке (с учетом аккумуляторных особенностей ;) ) очень утомительно.

4) !!! Обнаружен эффект пропуска байтов на приеме (скорость 57600). Чтобы понять, в чем дело, пришлось параллельно подключать компьютер с Гипертерминалом. На Гипертеминале символ есть, в Овене - нет. Большая скорость, недостаточный размер буфера?

5) Размер буфера установить нельзя. Почему? Это же не аппаратное квитирование, которое "не распаяно" :)

Филоненко Владислав
15.01.2009, 20:37
Поясню:
Библиотека стандартная, не нами придуманная.
0 - открытие успешно, (-1) - не успешно.
handle эквивалентно номеру порта. Что логично.
И в примерах использования дана простая последовательность, к-я гарантирует открытие порта независимо от того, был ли он открыт ранее (в т.ч. и после Reset-а). Но никто ни документацию, ни примеры не смотрит. Для Вас сделали: По Reset закрывается - обновите прошивку.
С двухэтапным открытием - опять вопрос не к нам, мы обязаны стандарт поддерживать.
Буфер огромен, пропуски возможны только если считывать редко. 1кБайт Вас не устраивает?
Полноценный 232 не распаян. Да и покажите мне контроллер такого форм-фактора с полноценным 232? 6 ног процессора дорогого стоят. А нужны 0,1% пользователей.
Всё оборудование, к-е подключали, прекрасно работало и на сокращённом.

alex1963
16.01.2009, 00:17
Поясню:
Библиотека стандартная, не нами придуманная.
0 - открытие успешно, (-1) - не успешно.
Да посмотрите английское описание - должен возвращаться handle, если успешно. Номер порта имеет тип PORTS, handle - DWORD. handle эквивалентно номеру порта? - да на здоровье. Но как раз-то стандарт не соблюден.

И в примерах использования дана простая последовательность, к-я гарантирует открытие порта независимо от того, был ли он открыт ранее (в т.ч. и после Reset-а). Вы про это? if open()=FFFFFFFF then close() open() end_if.
Это не "простая последоательность", а загадка в духе "что бы это значило". А как с сокетами и файлами?Начинать программу с циклов close() по всем возможным handle :)?

Буфер огромен, пропуски возможны только если считывать редко. 1кБайт Вас не устраивает? Считываю каждый цикл до read()=0. Тем не менее пропускает.

Вот ещё:
6) Если после SysComWrite() сразу делать SysComClose(), write(), похоже не работает. Нужно "подождать". Интересно, для файлов тоже нужно ждать, пока буфер сбросится?

Филоненко Владислав
16.01.2009, 15:51
if open()=FFFFFFFF then close() open() end_if. - нормальная последовательность, попробовал открыть - неудачно - значит уже открыт ранее, закрою и попробую снова.

16#FFFFFFFF - Это (-1), кто не догадался. Господин Петров подробно разъяснил ранее на форуме, откуда тут ноги растут.

Если после SysComWrite() сразу делать SysComClose(), write(), похоже не работает. Нужно "подождать". Интересно, для файлов тоже нужно ждать, пока буфер сбросится?

А как Вы хотите? Байты, они не мгновенно отсылаются, а один за одним.

Для файлов опасен только сброс, закрывайте без опаски, скорость записи ~60-100 кБайт в секунду. Размер буфера записи 30 кбайт.

Дмитрий Артюховский
18.01.2009, 12:22
самым главным приколом является то, что открывать порт, включать его, а затем использовать нужно в нескольких последовательных циклах контроллера .... хотя наверно это особенность любого сканирующего контроллера... но после компа очень не привычно ))) и пока дойдет смысл операции - проходит время. Причем в примере было написано, что между открытием и использованием должно пройти ВРЕМЯ, а не цикл контроллера

Филоненко Владислав
18.01.2009, 14:26
А у некоторых машин руль справа. И что? Пример как раз и был сделан чтобы люди его взяли, вставили в свою программу и не имели проблем.
Давайте перейдём в конструктивное русло.

alex1963
19.01.2009, 10:12
Конструктивное русло состоит в том, чтобы делать НАДЕЖНОЕ и УДОБНОЕ в использовании ПО, а не объяснять пользователю, как ему выкрутиться на том, что есть. Да, можно привыкнуть ездить на машине и с рулем справа (при правостороннем движении), но это неудобно и заботящаяся о сбыте автокомпания сделает исполнение с левым рулем.

Филоненко Владислав
19.01.2009, 10:32
НАДЕЖНОЕ === что бы не написал - всё работает? и УДОБНОЕ === инструкцию читать не надо?
Мы не молотки с интуитивно понятным интерфейсом выпускаем.

alex1963
19.01.2009, 13:31
НАДЕЖНОЕ === что бы не написал - всё работает?
Ну не всё, но по возможности, а если возможности нет - выдает признак ошибки :).
Например, когда пользователь закрывает порт, можно было бы и сбросить буфер, а затем уж закрывать. Ведь функции, определяющей, закончилась ли передача, нет.
И, разумеется, НАДЕЖНОЕ ПО не пропускает принимаемые байты, если оно не способно обеспечить безошибочный прием на определенной скорости, она просто не устанавливается. Почему пользователь должен догадываться, что 57600 "многовато будет" (на 19200 пропусков нет)?


УДОБНОЕ === инструкцию читать не надо?
Надо. Но прежде всего - программистам Овен. Тогда они не будут писать return 0; вместо return (DWORD)port_num; и пользователю не придется изучать различия ДВУХ инструкций - английской и русской, а программа, возможно, будет одинаково работать и в Сименсе, и в Адаме, и в Овене ;). Собственно, чтобы пользователю не нужно было так много читать, и придуманы стандарты - IEC1131-3, например ;).

Сейчас вот разбираюсь с SysLibTime.
Опять фирменные особенности :(. Естественно, в английском описании ни слова о том, что структуру нужно обнулять перед чтением времени. Но это еще мелочь. А вот:

Structure SysTime64
This structure contains the realtime of the local computer in microseconds. A Low- plus a High-DWORD
are used for that purpose, thus 64 Bit are available. The structure is used by the function blocks CurTime
and CurTimeEx.
Component Data type Description
ulLow DWORD Low DWORD of the realtime value (microseconds)
ulHigh DWORD High DWORD of the realtime value (microseconds)

1.SysTime: SysTime64;
SysTime
ulHigh: dword;
Содержит 0
ulLow: dword;
Содержит время с момента загрузки ПЛК в миллисекундах

Найдите 3 отличия :). Ответ. 1) Миллисекунды вместо микросекунд. 2) старшее слово не используется (программист получил премию за экономию 10 команд?). 3) Время с момента загрузки ПЛК вместо realtime.
А теперь скажите, как записать в переменную CodeSys типа DT текущую дату/время? Микросекунды в секунды перевести и упаковать в одно слово было бы несложно, а вот вспоминать сколько дней в каждом месяце и какие годы високосные - брр :(.

Филоненко Владислав
19.01.2009, 13:44
про пропуски - ни разу не наблюдалось. Возможно уровни сигналов не стандартные или емкость линии велика?

Про установку времени:
SysLibTime.lib не позволяет этого сделать - пришлось подшаманить.

Про время - уже в точности по описанию из CoDeSys. Давно.

А как ВЫ представляете себе реальное время в микросекундах. Значит стоит ПЛК за 7000 р. и к нему присобачена 5-ти тонная установка - квантовые атомные часы за 70000000$ ?
Поэтому секунды и выше - реальное время, а
ulLow DWORD Low DWORD of the realtime value (microseconds)
ulHigh DWORD High DWORD of the realtime value (microseconds)
с момента загрузки.
И могу поспорить, что во ВСЕХ ПЛК сделано аналогично.

Игорь Петров
19.01.2009, 14:18
:cool: Могу теперь понять, почему известные западные изготовители ПЛК делают такое ограниченное ПО для своих классических моделей. Если поддержано МЭК программирование, то операций с файлами просто нет (не говоря уже о сокетах и тем более указателях) и до свидания! Выбрасывают все, что может вызывать сложности у массового пользователя, оставляют базовое ядро самых ходовых команд. Шаг влево, шаг вправо – нельзя, покупай для этого устройство другого класса. Контроллеры применяются только в своей узкой нише. Их программирование получается очень простым и надежным. Естественно никаких Кулибинских трюков на таких ПЛК делать нельзя. Они намеренно запрещены. Купил вилку для рыбы на пару – используй ее для рыбы и не спрашивай, почему ею не удобно открывать пиво.

:confused: Овен зачем-то старается идти на встречу всем пользователям, включая очень продвинутых. В результате, последние имеют возможность творить чудеса с ПЛК. Вплоть до того, что пишут свои языки и интерпретаторы для систем управления перемещениями, делая на ПЛК автоматы и роботы, обычно требующие стоики ЧПУ (в 20 раз дороже и вообще из другого мира).
Системные библиотеки (SysLib…) это типовой функционал компьютеров втянутый в ПЛК. Он вообще очень криво лезет в модель классического сканирующего ПЛК. Например, описанная выше проблема открытия файлов, портов. Тут есть 2 варианта: 1) Синхронные функции. Функция не отдает управление пока не отработает (например, не задвинет всю строку в буфер передатчика). Так делают в компьютерах. Это чревато тем, что можно прозевать другие события, часто гораздо более важные в задачах управления реального времени. Придется однозначно делать проект многозадачным, брать толстые учебники и разбираться с синхронизацией потоков, семафорами и др. и пр. 2) Асинхронные функции. Они возвращают управление сразу. Пользовательская программа пошла работать дальше, а функция в фоне еще завершает свою работу. Тут конечно тоже нельзя совсем тупо программировать. Открытие потоков и их обслуживание надо аккуратно размазать по управляющим циклам. В принципе это не столь сложно. Один раз сделать, чтобы заработало и все.
Технически у Овен все сделано очень разумно. Другой вопрос в том, что это нестандартные штуки, сложных вопросов тут много, мирового опыта их описывать всем понятным языком просто не существует. ИМХО выбросить бы все упоминания про системные биб-ки из документации и давать их только по запросу. Сразу бы вопросов на этом форуме стало раз в 10 меньше.

:o Со стороны CoDeSys: тема старая, больная. 'Глюки' эти, точнее разночтения вылезают у всех изготовителей ПЛК. Причем у многих, гораздо хуже. Изначально системные библиотеки сделаны как некие шаблоны, которые по мере возможности желательно соблюдать, если это не усложняет их разработку. Не более того. Разные ОС, разные процессоры тянут специфику. Системные биб-ки аппаратно зависимы и имеют полное право отличаться! Поэтому их и не вносят в стандартные. Мало того, в системе хелпа CoDeSys даже предусмотрена возможность отключать описания определенных библиотек и заменять их на свои, при выборе другой модели ПЛК! Поэтому при наличии фирменного описания системной биб-ки не в коем случае не надо читать ее описание от 3S или другого изготовителя ПЛК. Эти описания близко не претендуют на роль более стандартных или более правильных.
Что делается для исправления ситуации? Есть организация такая CoDeSys Automation Alliance, объединяющая изготовителей контроллеров. Ее силами идет разработка библиотек CAA, которые должны сменить системные. Их нужно тщательно проработать, дабы сделать их можно было для любых типов процессоров и ОС существующих в мире. Это не очень просто. Кроме того, выполняется работа по разработке специальных тестов для проверки совместимости. О сроках пока говорить рано.