Содержание
- Функция ClearCommError
- Странное поведение функции ClearCommError
- 31.10.2017
- ClearCommError function (winbase.h)
- Syntax
- Parameters
- Return value
- Remarks
- Clearcommerror failed winapi error 22
Функция ClearCommError
Функция ClearCommError извлекает информацию об коммуникационной ошибке и сообщает о текущем состоянии коммуникационного устройства. Функция вызывается тогда, когда происходит ошибка обмена информацией и сбрасывает флажок ошибки устройства, чтобы включить в работу дополнительные операции ввода и вывода данных (I/O).
[in] Дескриптор коммуникационного устройства. Функция CreateFile возвращает этот дескриптор.
[out] Указатель на переменную, которая составляет маску, указывающую тип ошибки. Этот параметр может состоять из одного или нескольких ниже перечисленных значений.
Значение | Предназначение |
---|---|
CE_BREAK | Аппаратные средства обнаружили условие прерывания. |
CE_DNS | Windows Me/98/95: Параллельное устройство не выбрано. |
CE_FRAME | Аппаратные средства обнаружили ошибку кадровой синхронизации. |
CE_IOE | Ошибка ввода — вывода (I/O) произошла в ходе обмена информацией с устройством. |
CE_MODE | Затребованный режим не поддерживается, или недопустим параметр hFile. Если это значение устанавливается, то это — единственная допустимая ошибка. |
CE_OOP | Windows Me/98/95: Параллельное устройство сообщило, что оно является за пределами листа бумаги. |
CE_OVERRUN | Произошло переполнение буфера символов. Следующий символ потерялся. |
CE_PTO | Windows Me/98/95: Произошел перерыв в работе на параллельном устройстве. |
CE_RXOVER | Произошло переполнение буфера ввода данных. Или нет места в буфере ввода данных, или символ был получен после метки конца файла (EOF). |
CE_RXPARITY | Аппаратные средства обнаружили ошибку четности. |
CE_TXFULL | Приложение пыталось передать символ, но буфер вывода данных был заполнен. |
Если функция завершается успешно, возвращаемое значение не нуль.
Если функция завершается ошибкой, возвращаемое значение равняется нулю. Чтобы получить дополнительную информацию об ошибке, вызовите GetLastError.
Если коммуникационный порт установлен со значением ИСТИНА (TRUE) в члене fAbortOnError структуры установки программы DCB, коммуникационная программа завершит работу всех операций чтения и записи на коммуникационном порте, когда происходит коммуникационная ошибка. Новые операции чтения или записи не должны допускаться до тех пор, пока прикладная программа не опознает коммуникационную ошибку при помощи вызова функция ClearCommError.
Функция ClearCommError заполняет буфер состояния, на который указывает параметр lpStat текущим состоянием коммуникационного устройства, определенного параметром hFile.
Размещение и совместимость ClearCommError
Источник
Странное поведение функции ClearCommError
31.10.2017
Некоторое время назад при работе над одной программой я столкнулся с необычным поведением функции ClearCommError. Задача была довольно простой: есть прибор, от которого по COM порту принимаются данные. Вроде бы ничего сложного, но меня ждал подвох.
Для приема данных был реализован отдельный поток, который пробуждался каждый раз при поступлении данных в порт. При этом управление получал приблизительно такой код:
Какого же было мое удивление, когда я обнаружил, что он не работает. Точнее работает, но крайне нестабильно. Почему? во время отладки выяснилось, что проблема в функции ClearCommError, которая неправильно заполняла структуру COMSTAT. Точнее она неправильно определяла размер данных, поступивших в порт. Прибор, от которого я принимал данные, работал с известной частотой, размер данных отправляемых им за один раз также известен. Поэтому оценить сколько должно приходить — не проблема. Функция ClearCommError на разных итерациях определяла размер принятых байт то в 4096, то в 2, то в 3 байта. Неслабый разброс. Может я делаю что-то не так?
Согласно документации функция ClearCommError предназначена для сброса ошибки COM порта. Может быть для определения размера полученных данных нужно использовать какую-то другую функцию? Я полез в Интернет. Но ничего не нашел. Во всех найденных мною примерах размер полученных данных определялся именно этой функцией. Других функций нет. Так в чем дело?
Поиск в Интернете все-таки дал свои плоды. Оказывается я не первый кто столкнулся с такой проблемой. ее обсуждение можно найти на форуме vingrad (ссылка). К сожалению, красивого решения найти не удалось. Поэтому пришлось использовать функцию ClearCommError в цикле. Пример кода:
Данный код работает стабильно и пока ни разу не подводил меня. Может показаться что цикл создает нагрузку на процессор, но это не так. Дело в том, что данный цикл запускается только при поступлении какой-либо информации в порт. Поэтому он обрабатывает только действительно нужные данные.
Источник
ClearCommError function (winbase.h)
Retrieves information about a communications error and reports the current status of a communications device. The function is called when a communications error occurs, and it clears the device’s error flag to enable additional input and output (I/O) operations.
Syntax
Parameters
A handle to the communications device. The CreateFile function returns this handle.
[out, optional] lpErrors
A pointer to a variable that receives a mask indicating the type of error. This parameter can be one or more of the following values.
Value | Meaning |
---|---|
CE_BREAK 0x0010 | The hardware detected a break condition. |
CE_FRAME 0x0008 | The hardware detected a framing error. |
CE_OVERRUN 0x0002 | A character-buffer overrun has occurred. The next character is lost. |
CE_RXOVER 0x0001 | An input buffer overflow has occurred. There is either no room in the input buffer, or a character was received after the end-of-file (EOF) character. |
CE_RXPARITY 0x0004 | The hardware detected a parity error. |
В
The following values are not supported:
[out, optional] lpStat
A pointer to a COMSTAT structure in which the device’s status information is returned. If this parameter is NULL, no status information is returned.
Return value
If the function succeeds, the return value is nonzero.
If the function fails, the return value is zero. To get extended error information, call GetLastError.
If a communications port has been set up with a TRUE value for the fAbortOnError member of the setup DCB structure, the communications software will terminate all read and write operations on the communications port when a communications error occurs. No new read or write operations will be accepted until the application acknowledges the communications error by calling the ClearCommError function.
The ClearCommError function fills the status buffer pointed to by the lpStat parameter with the current status of the communications device specified by the hFile parameter.
Источник
Clearcommerror failed winapi error 22
Профиль
Группа: Участник
Сообщений: 2
Регистрация: 12.3.2013
Репутация: нет
Всего: нет
Помогите пожалуйста разобраться с ClearCommError. Вообще первый раз пытаюсь в Delphi что то делать, но необходимость нагрянула.
На com порте висит заглушка с соединёнными RX и TX. т.е. что выдаётся, то сразу попадает в буфер чтения. Запущен монитор, позволяющий всё это дело контролировать.
Смог накорябать, в меру соображения, вот это:
zagma |
|
||
Код |
program writfile; |
hFile :THandle;
ByteWritten : cardinal;
temp :string; // это будет отправляться
namefile:Pchar; // имя файла
COMStat: TCOMStat; // переменная для определения данных в буфере
xn: THandle;
begin
temp:=’Hello World!’; // строка для записи в файл
namefile:=’COM3′; // Имя файла для создания
hFile:= CreateFile(namefile,GENERIC_READ or GENERIC_WRITE,
FILE_SHARE_READ or FILE_SHARE_WRITE,nil,CREATE_ALWAYS,0,0); // Открывается порт
WriteFile(hFile, temp[1], Length(temp),ByteWritten, nil); // пишется строка в порт
ClearCommError(hFile,xn,@COMStat); //получаем состояние COM в StatCOM
xn:=COMStat.cbInQue; // в cblnQue должно вроде быть количество байтов в буфере
ShowMessage(IntTostr(xn)) ; // показывается сколько ж там чего — ДЫРКА ТАМ . НОЛЬ
ReadFile(hFile,MyBuff,SizeOf(MyBuff),ByteReaded,Nil); // строка из буфера считывается . ВПОЛНЕ ОДУШЕВЛЁННАЯ .
Может подскажете, что я не так сделал (или не сделал). Показывает cblnQue = 0, когда в буфере 12 байт.
northener |
|
||
Эксперт Профиль Репутация: 12
На момент вызова процедуры ClearCommError в буфере нет ещё ничего. Добавлено через 2 минуты и 21 секунду |
|||
|
Профиль
Группа: Участник
Сообщений: 2
Регистрация: 12.3.2013
Репутация: нет
Всего: нет
zagma |
|
||
Цитата(zagma @ 12.3.2013, 20:26 ) |
Может подскажете, что я не так сделал (или не сделал). Показывает cblnQue = 0, когда в буфере 12 байт. |
На момент вызова процедуры ClearCommError в буфере нет ещё ничего.
А функция ReadFile будет ждать пока не прочитает что-то из буфера, либо пока не истечет установленный таймаут.
Добавлено @ 20:51
Вот неплохая статья по работе с СОМ-портом:
Работа с СОМ-портом в Windows (W9x, W2k)
1. Публиковать ссылки на вскрытые компоненты
2. Обсуждать взлом компонентов и делиться вскрытыми компонентами
- Литературу по Дельфи обсуждаем здесь
- Действия модераторов можно обсудить здесь
- С просьбами о написании курсовой, реферата и т.п. обращаться сюда
- Вопросы по реализации алгоритмов рассматриваются здесь
- 90% ответов на свои вопросы можно найти в DRKB (Delphi Russian Knowledge Base) — крупнейшем в рунете сборнике материалов по Дельфи
Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, Snowy, MetalFan, bems, Poseidon, Rrader.
Правила форума «Delphi: Для новичков» |
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей) |
0 Пользователей: |
« Предыдущая тема | Delphi: Для новичков | Следующая тема » |
[ Время генерации скрипта: 0.0909 ] [ Использовано запросов: 21 ] [ GZIP включён ]
Источник
Adblock
detector
Всем доброго времени суток, я вообще не программист, программирую от случая к случаю, пишу программу для работы с Com портом, котрая должна общаться с таблом типа LED MATRIX. От компонентов решил отказаться, пишу на WinAPI. Мне нужно интерпретировать значения отправляемые функцией ClearCommError в одну из переменных, а именно в lpErrors
Вот объявление функции в Windows.pas:
Delphi | ||
|
Вот что нарыл в инете про эту переменную (lpErrors), как вставить риунок в конкретное место я не понял см в миниатюрах.
Значения флагов CE_BREAK и т.д. естественно тоже объявлены в Виндовс.пас, вот они:
Delphi | ||
|
Отлаживаю программу, и смотрю какое значение отправляется в lpErrors, фактическая переменная Errs:
Delphi | ||
|
И в Watch List-е вижу:
WatchName: Errs
Value: $12F95C — смотрю в Хексе
А теперь внимание вопрос — как мне интерпретировать данное значение, с учетом того, что может быть установлено несколько бит как написано (см рис).
__________________
Помощь в написании контрольных, курсовых и дипломных работ, диссертаций здесь
win32 (64 bit python), pyserial 3.4, connecting to a u-blox virtual serial port (installed using latest version of u-center, v21.02, see https://www.u-blox.com/en/product/u-center).
It seems that whenever ClearCommError is called, an errno 22 (The parameter is incorrect) is thrown.
File «./external/serial/serialwin32.py», line 273, in read
serial.serialutil.SerialException: ClearCommError failed (OSError(22, ‘The parameter is incorrect.’, None, 87))
I was able to continue after monkeypatching ClearCommError:
oce = serial.win32.ClearCommError def ClearCommError(hwnd, flags, comstat): ret = oce(hwnd, flags, comstat) if not ret: winerr = ctypes.WinError() if winerr.errno == 22: return True return ret if type(oce) is not types.FunctionType: serial.win32.ClearCommError = ClearCommError
I wonder if this is an issue with pre-emptively calling ClearCommError with no error present?
However, I can’t find a way to check if an error is present on a comport, other than simply attempt read/write/whatever.
Некоторое время назад при работе над одной программой я столкнулся с необычным поведением функции ClearCommError. Задача была довольно простой: есть прибор, от которого по COM порту принимаются данные. Вроде бы ничего сложного, но меня ждал подвох.
Для приема данных был реализован отдельный поток, который пробуждался каждый раз при поступлении данных в порт. При этом управление получал приблизительно такой код:
COMSTAT comstat; unsigned long temp; //Определяем размер поступивших данных ClearCommError(hCOM, &temp, &comstat); if(comstat.cbInQue > size_buffer) { //Если нужно увеличиваем размер буфера под данные pbuffer = realloc(pbuffer, comstat.cbInQue); size_buffer = comstat.cbInQue; } //Читаем данные DWORD fact_size = 0; ReadFile(hCOM, pbuffer, comstat.cbInQue, &fact_size, &overlapped); //Обрабатываем данные PerformData(fact_size);
Какого же было мое удивление, когда я обнаружил, что он не работает. Точнее работает, но крайне нестабильно. Почему? во время отладки выяснилось, что проблема в функции ClearCommError, которая неправильно заполняла структуру COMSTAT. Точнее она неправильно определяла размер данных, поступивших в порт. Прибор, от которого я принимал данные, работал с известной частотой, размер данных отправляемых им за один раз также известен. Поэтому оценить сколько должно приходить — не проблема. Функция ClearCommError на разных итерациях определяла размер принятых байт то в 4096, то в 2, то в 3 байта. Неслабый разброс. Может я делаю что-то не так?
Согласно документации функция ClearCommError предназначена для сброса ошибки COM порта. Может быть для определения размера полученных данных нужно использовать какую-то другую функцию? Я полез в Интернет. Но ничего не нашел. Во всех найденных мною примерах размер полученных данных определялся именно этой функцией. Других функций нет. Так в чем дело?
Поиск в Интернете все-таки дал свои плоды. Оказывается я не первый кто столкнулся с такой проблемой. ее обсуждение можно найти на форуме vingrad (ссылка). К сожалению, красивого решения найти не удалось. Поэтому пришлось использовать функцию ClearCommError в цикле. Пример кода:
COMSTAT comstat; unsigned long temp; //Определяем размер поступивших данных ClearCommError(hCOM, &temp, &comstat); while(comstat.cbInQue) { //Определяем размер чтобы уместиться в буфер unsigned long size; size = (comstat.cbInQue < size_buffer) ? comstat.cbInQue : size_buffer; //Читаем данные unsigned long fact_size = 0; ReadFile(hCOM, pbuffer, size, &fact_size, &overlapped); //Обрабатываем данные PerformData(fact_size); //Проверяем все ли мы прочитали из COM порта ClearCommError(hCOM, &temp, &comstat); }
Данный код работает стабильно и пока ни разу не подводил меня. Может показаться что цикл создает нагрузку на процессор, но это не так. Дело в том, что данный цикл запускается только при поступлении какой-либо информации в порт. Поэтому он обрабатывает только действительно нужные данные.
Форум программистов Vingrad
Модераторы: Snowy, MetalFan, bems, Poseidon |
Поиск: |
|
Помогите разобраться с ClearCommError |
Опции темы |
zagma |
|
||
Новичок Профиль Репутация: нет
|
Помогите пожалуйста разобраться с ClearCommError. Вообще первый раз пытаюсь в Delphi что то делать, но необходимость нагрянула. Смог накорябать, в меру соображения, вот это:
Может подскажете, что я не так сделал (или не сделал). Показывает cblnQue = 0, когда в буфере 12 байт. |
||
|
|||
northener |
|
||
Эксперт Профиль Репутация: 12
|
На момент вызова процедуры ClearCommError в буфере нет ещё ничего. Добавлено через 2 минуты и 21 секунду ——————— Но только лошади летают вдохновенно. |
||
|
|||
zagma |
|
||||
Новичок Профиль Репутация: нет
|
То есть, то что передано WriteFile ещё не принято или ещё передаётся, так? ….. Точно! …. подождал немного и вернулось двенадцать! Спасибо большое и за подсказку и за статью ! |
||||
|
|||||
|
Правила форума «Delphi: Для новичков» | |
|
Запрещается! 1. Публиковать ссылки на вскрытые компоненты 2. Обсуждать взлом компонентов и делиться вскрытыми компонентами
Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, Snowy, MetalFan, bems, Poseidon, Rrader. |
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей) |
0 Пользователей: |
« Предыдущая тема | Delphi: Для новичков | Следующая тема » |
На чтение 6 мин Обновлено 15.01.2023
Clearcommerror failed winapi error 22
Профиль
Группа: Участник
Сообщений: 2
Регистрация: 12.3.2013
Репутация: нет
Всего: нет
Помогите пожалуйста разобраться с ClearCommError. Вообще первый раз пытаюсь в Delphi что то делать, но необходимость нагрянула.
На com порте висит заглушка с соединёнными RX и TX. т.е. что выдаётся, то сразу попадает в буфер чтения. Запущен монитор, позволяющий всё это дело контролировать.
Смог накорябать, в меру соображения, вот это:
zagma |
|
||
Код |
program writfile; |
hFile :THandle;
ByteWritten : cardinal;
temp :string; // это будет отправляться
namefile:Pchar; // имя файла
COMStat: TCOMStat; // переменная для определения данных в буфере
xn: THandle;
begin
temp:=’Hello World!’; // строка для записи в файл
namefile:=’COM3′; // Имя файла для создания
hFile:= CreateFile(namefile,GENERIC_READ or GENERIC_WRITE,
FILE_SHARE_READ or FILE_SHARE_WRITE,nil,CREATE_ALWAYS,0,0); // Открывается порт
WriteFile(hFile, temp[1], Length(temp),ByteWritten, nil); // пишется строка в порт
ClearCommError(hFile,xn,@COMStat); //получаем состояние COM в StatCOM
xn:=COMStat.cbInQue; // в cblnQue должно вроде быть количество байтов в буфере
ShowMessage(IntTostr(xn)) ; // показывается сколько ж там чего — ДЫРКА ТАМ . НОЛЬ
ReadFile(hFile,MyBuff,SizeOf(MyBuff),ByteReaded,Nil); // строка из буфера считывается . ВПОЛНЕ ОДУШЕВЛЁННАЯ .
Может подскажете, что я не так сделал (или не сделал). Показывает cblnQue = 0, когда в буфере 12 байт.
northener |
|
||
Эксперт Профиль Репутация: 12
На момент вызова процедуры ClearCommError в буфере нет ещё ничего. Добавлено через 2 минуты и 21 секунду |
|||
|
Профиль
Группа: Участник
Сообщений: 2
Регистрация: 12.3.2013
Репутация: нет
Всего: нет
zagma |
|
||
Цитата(zagma @ 12.3.2013, 20:26 ) |
Может подскажете, что я не так сделал (или не сделал). Показывает cblnQue = 0, когда в буфере 12 байт. |
На момент вызова процедуры ClearCommError в буфере нет ещё ничего.
А функция ReadFile будет ждать пока не прочитает что-то из буфера, либо пока не истечет установленный таймаут.
Добавлено @ 20:51
Вот неплохая статья по работе с СОМ-портом:
Работа с СОМ-портом в Windows (W9x, W2k)
1. Публиковать ссылки на вскрытые компоненты
2. Обсуждать взлом компонентов и делиться вскрытыми компонентами
- Литературу по Дельфи обсуждаем здесь
- Действия модераторов можно обсудить здесь
- С просьбами о написании курсовой, реферата и т.п. обращаться сюда
- Вопросы по реализации алгоритмов рассматриваются здесь
- 90% ответов на свои вопросы можно найти в DRKB (Delphi Russian Knowledge Base) — крупнейшем в рунете сборнике материалов по Дельфи
Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, Snowy, MetalFan, bems, Poseidon, Rrader.
Правила форума «Delphi: Для новичков» |
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей) |
0 Пользователей: |
« Предыдущая тема | Delphi: Для новичков | Следующая тема » |
[ Время генерации скрипта: 0.0917 ] [ Использовано запросов: 21 ] [ GZIP включён ]
Источник
Функция ClearCommError
Функция ClearCommError извлекает информацию об коммуникационной ошибке и сообщает о текущем состоянии коммуникационного устройства. Функция вызывается тогда, когда происходит ошибка обмена информацией и сбрасывает флажок ошибки устройства, чтобы включить в работу дополнительные операции ввода и вывода данных (I/O).
[in] Дескриптор коммуникационного устройства. Функция CreateFile возвращает этот дескриптор.
[out] Указатель на переменную, которая составляет маску, указывающую тип ошибки. Этот параметр может состоять из одного или нескольких ниже перечисленных значений.
Значение | Предназначение |
---|---|
CE_BREAK | Аппаратные средства обнаружили условие прерывания. |
CE_DNS | Windows Me/98/95: Параллельное устройство не выбрано. |
CE_FRAME | Аппаратные средства обнаружили ошибку кадровой синхронизации. |
CE_IOE | Ошибка ввода — вывода (I/O) произошла в ходе обмена информацией с устройством. |
CE_MODE | Затребованный режим не поддерживается, или недопустим параметр hFile. Если это значение устанавливается, то это — единственная допустимая ошибка. |
CE_OOP | Windows Me/98/95: Параллельное устройство сообщило, что оно является за пределами листа бумаги. |
CE_OVERRUN | Произошло переполнение буфера символов. Следующий символ потерялся. |
CE_PTO | Windows Me/98/95: Произошел перерыв в работе на параллельном устройстве. |
CE_RXOVER | Произошло переполнение буфера ввода данных. Или нет места в буфере ввода данных, или символ был получен после метки конца файла (EOF). |
CE_RXPARITY | Аппаратные средства обнаружили ошибку четности. |
CE_TXFULL | Приложение пыталось передать символ, но буфер вывода данных был заполнен. |
Если функция завершается успешно, возвращаемое значение не нуль.
Если функция завершается ошибкой, возвращаемое значение равняется нулю. Чтобы получить дополнительную информацию об ошибке, вызовите GetLastError.
Если коммуникационный порт установлен со значением ИСТИНА (TRUE) в члене fAbortOnError структуры установки программы DCB, коммуникационная программа завершит работу всех операций чтения и записи на коммуникационном порте, когда происходит коммуникационная ошибка. Новые операции чтения или записи не должны допускаться до тех пор, пока прикладная программа не опознает коммуникационную ошибку при помощи вызова функция ClearCommError.
Функция ClearCommError заполняет буфер состояния, на который указывает параметр lpStat текущим состоянием коммуникационного устройства, определенного параметром hFile.
Размещение и совместимость ClearCommError
Источник
ClearCommError function (winbase.h)
Retrieves information about a communications error and reports the current status of a communications device. The function is called when a communications error occurs, and it clears the device’s error flag to enable additional input and output (I/O) operations.
Syntax
Parameters
A handle to the communications device. The CreateFile function returns this handle.
[out, optional] lpErrors
A pointer to a variable that receives a mask indicating the type of error. This parameter can be one or more of the following values.
Value | Meaning |
---|---|
CE_BREAK 0x0010 | The hardware detected a break condition. |
CE_FRAME 0x0008 | The hardware detected a framing error. |
CE_OVERRUN 0x0002 | A character-buffer overrun has occurred. The next character is lost. |
CE_RXOVER 0x0001 | An input buffer overflow has occurred. There is either no room in the input buffer, or a character was received after the end-of-file (EOF) character. |
CE_RXPARITY 0x0004 | The hardware detected a parity error. |
В
The following values are not supported:
[out, optional] lpStat
A pointer to a COMSTAT structure in which the device’s status information is returned. If this parameter is NULL, no status information is returned.
Return value
If the function succeeds, the return value is nonzero.
If the function fails, the return value is zero. To get extended error information, call GetLastError.
Remarks
If a communications port has been set up with a TRUE value for the fAbortOnError member of the setup DCB structure, the communications software will terminate all read and write operations on the communications port when a communications error occurs. No new read or write operations will be accepted until the application acknowledges the communications error by calling the ClearCommError function.
The ClearCommError function fills the status buffer pointed to by the lpStat parameter with the current status of the communications device specified by the hFile parameter.
Источник
Читайте также: Syntax error near lua
Adblock
detector