Передача сообщений через последовательный порт


Добавил:DMT
Дата создания:23 апреля 2008, 21:11
Дата обновления:23 апреля 2008, 21:21
Просмотров:12404 последний вчера, 21:26
Комментариев: 0

Передача сообщений через последовательный порт.

Задание : Два компьютера соединены 0-модемным кабелем через последовательные порты. Написать программы приема и передачи сообщений через последовательный порт с параметрами связи по вариантам. Сообщение, при наборе с клавиатуры, хранится в буфере и отправляется по нажатию клавиши [ Enter ].

Передача байта через порт

Количество стоповых бит

Контроль четности

Скорость обмена (бод)

По опросу

1

По четности

300

 

Описание настройки регистра управления линией:

0-1 бит – Длина передаваемого слова

2 бит - Стоповый бит

3-4 бит - Биты четности

5 бит - Бит фиксации четности

6 бит - Бит установки перерыва

7 бит - Бит DLAB

 

Для нашей программы было установлена последовательность битов: 00011011, т.е.

Длина передаваемого слова 8 бит,

Количество стоповых битов: 1,

Контроль четности: По четности,

Фиксация четности, если стоит четность, то фиксация 0.

Бит установки перерыва и бит DLAB не рассматривались и установлены в 0 .

Передающая программа:
Код на ASM
  1. .model tiny
  2. .code
  3. org 100h
  4. .486
  5. start:
  6. ;инициализация последовательного порта COM1
  7. mov dx, b ;В dx номер порта регистра управления линией.
  8. in al, dx ;Считываем байт из управляющего регистра в al,
  9. or al, 10000000b ;устанавливаем старший бит в 1 (DLAB=1) и
  10. out dx, al ;измененный байт записываем в управляющий регистр.
  11. ;Т.е. по портам 3F8 и 3F9 находятся:
  12. ;регистры младшего и старшего байта делителя.
  13. mov al, 80h ;Записываем в al младший байт делителя
  14. mov dx, p8 ;для скорости 300 бод и
  15. out dx, al ;помещаем его в порт 3f8.
  16. mov al, 01h ;Записываем в al старший байт делителя
  17. mov dx, p9 ;для скорости 300 бод и
  18. out dx, al ;помешаем его в порт 3f9.
  19.  
  20. mov dx, b ;В dx номер порта регистра управления линией.
  21. in al, dx ;Записываем байт из управляющего регистра в al и
  22. and al, 01111111b ;устанавливаем старший бит в 0 (DLAB=0),
  23. out dx, al ;измененный байт записываем в управляющий
  24. ;регистр.
  25. ;Т.е. по портам 3F8 и 3F9 теперь находятся регистр хранения
  26. ;передатчика и регистр управления прерыванием.
  27.  
  28. mov al, 00011011b ;Записываем информацию о формате кадра
  29. out dx, al ;в управляющий регистр (3FB).
  30. mov al, 00h ;Запрещаем генерацию прерывания
  31. mov dx, p9 ;через регистр управления прерыванием.
  32. out dx, al
  33. ;передача байта
  34. mainloop:
  35. xor ax, ax ;ax<-0000h
  36. mov ah, 1 ;считываем байт с клавиатуры
  37. int 21h
  38. cmp al, 27 ;если нажата клавиша ESC, то
  39. je endloop ;выходим из программы, иначе
  40. mov bl, al ;сохраняем информационный байт
  41. waitloop: ;цикл опроса порта состояния линии
  42. mov dx, d ;В dx регистр состояния (статуса) линии.
  43. in al, dx ;Считываем состояние линии в al.
  44. and al, 00100000b ;обнуляем все биты кроме 5-го и
  45. cmp al, 00000000b ;если 5-ый бит порта состояния равен нулю
  46. ;(предыдущие данные еще не переданы), то
  47. je waitloop ;ждем, пока он не установлен.
  48. mov al, bl ;Если установлен, то
  49. mov dx, p8 ;посылаем информационный байт в
  50. out dx, al ; регистр данных передатчика
  51. jmp mainloop ;переходим к пересылке следующего символа
  52. endloop:
  53. ret ;КОНЕЦ ПРОГРАММЫ
  54. p8 dw 3f8h ;Регистр хранения передатчика (DLAB =0)
  55. ;Младший делитель скорости обмена (DLAB =1)
  56. p9 dw 3f9h ;Регистр управления (разрешения) прерыванием
  57. ;(DLAB =0)
  58. ;Старший делитель скорости обмена (DLAB =1)
  59. b dw 3fbh ;Регистр управления линией
  60. c dw 3fch ;Регистр управления модемом
  61. d dw 3fdh ;Регистр состояния (статуса) линии
  62. end start
При использовании обязательна ссылка на http://DMTSoft.ru
Принимающая программа:
Код на ASM
  1. .model tiny
  2. .code
  3. org 100h
  4. .486
  5. start:
  6. ;инициализация последовательного порта COM1
  7. mov dx, b ;В dx номер порта регистра управления линией.
  8. in al, dx ;Считываем байт из управляющего регистра в al,
  9. or al, 10000000b ;устанавливаем старший бит в 1 (DLAB=1) и
  10. out dx, al ;измененный байт записываем в управляющий регистр.
  11.  
  12. ;Т.е. по портам 3F8 и 3F9 находятся: регистры младшего и старшего байта делителя.
  13. mov al, 80h ;Записываем в al младший байт делителя
  14. mov dx, p8 ;для скорости 300 бод и
  15. out dx, al ;помещаем его в порт 3f8.
  16. mov al, 01h ;Записываем в al старший байт делителя
  17. mov dx, p9 ;для скорости 300 бод и
  18. out dx, al ;помешаем его в порт 3f9.
  19. mov dx, b ;В dx номер порта регистра управления линией.
  20. in al, dx ;Записываем байт из управляющего регистра в al и
  21. and al, 01111111b ;устанавливаем старший бит в 0 (DLAB=0),
  22. out dx, al ;измененный байт записываем в управляющий ;регистр.
  23. ;Т.е. по портам 3F8 и 3F9 теперь находятся регистр хранения ;передатчика и регистр управления прерыванием.
  24. mov al, 00011011b ;Записываем информацию о формате кадра
  25. out dx, al ;в управляющий регистр (3FB).
  26. mov al, 00h ;Запрещаем генерацию прерывания
  27. mov dx, p9 ;через регистр управления прерыванием.
  28. out dx, al
  29. ;прием байта
  30. mainloop: ;Цикл опроса состояния линии.
  31. mov dx, d ;В dx регистр состояния (статуса) линии.
  32. in al, dx ;Считываем состояние линии в al.
  33. and al, 00000001b ;Обнуляем все биты кроме 0-го и
  34. cmp al, 00000000b ;если 0-ый бит порта состояния равен нулю
  35. ;(данные еще не получены), то
  36. je mainloop ;ждем, пока он не установлен.
  37. ;Если установлен (данные получены и готовы для чтения), то
  38. mov dx, p8 ;принимаем байт из регистра данных приемника
  39. in al, dx ;через порт 3F8.
  40. cmp al, 9 ;Сравниваем принятый символ на Tab.
  41. je endloop ;Если Tab, то завершаем выполнение программы, иначе
  42. mov dl, al ;выводим принятый байт на экран.
  43. mov ah, 2
  44. int 21h
  45. jmp mainloop ;переходим к приему следующего символа.
  46. endloop:
  47. ret ;КОНЕЦ ПРОГРАММЫ
  48. p8 dw 3f8h ;Регистр хранения передатчика (DLAB =0)
  49. ;Младший делитель скорости обмена (DLAB =1)
  50. p9 dw 3f9h ;Регистр управления (разрешения) прерыванием
  51. ;(DLAB =0)
  52. ;Старший делитель скорости обмена (DLAB =1)
  53. b dw 3fbh ;Регистр управления линией
  54. c dw 3fch ;Регистр управления модемом
  55. d dw 3fdh ;Регистр состояния (статуса) линии
  56. end start
При использовании обязательна ссылка на http://DMTSoft.ru

Описание асинхронного последовательного порта и примеры программ для выполнения контрольных работ.

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

Каждый кадр данных, передаваемых через последовательный порт, состоит из следующей последовательности сигнальных битов:

1. Один стартовый бит;

2. До 8 бит данных;

3. Необязательный бит четности;

4. Один, полтора или два стоповых бита.

Стартовый бит передаваемой "порции" данных (имеет нулевое значение) сигнализирует о начале передачи нового байта, который передается в канал за один цикл, начиная с младшего бита. Вслед за битами данных передается необязательный бит четности.

Бит четности, если он присутствует в передаваемом сообщении, используется для контроля корректности передачи и поиска ошибок. Контроль передачи может проводиться как на четность (контрольный разряд равен сумме по модулю 2 информационных разрядов и общее число единичных разрядов четно), так и на нечетность (контрольный разряд не равен сумме по модулю 2 информационных разрядов и общее число единичных разрядов нечетно).

В конце пересылаются стоповые биты (имеют значение равное единице) сигнализирующие о конце очередной "порции" данных считанных за один цикл. Завершающие (конечные) биты определяют минимальное время между передачей двух кадров. Обычно число завершающих битов не имеет большого значения, поэтому можно использовать либо один, либо два завершающих бита в зависимости от того, какое их число используют передающий и принимающий порты.

Между передачей каждого кадра может проходить некоторый промежуток времени. Время простоя канала передачи для этого режима довольно велико.

Передатчик и приемник должны использовать один и тот же формат данных и соблюдать одинаковую скорость передачи данных (в бодах).

Скорость передачи битов по каналу измеряется в бодах (бит в секунду). Наименьшей скоростью передачи информации считается 300 бод. Эта скорость передачи использовалась в старых модемах. Семейство компьютеров IBM PC поддерживает скорость передачи данных до частоты тактового генератора контроллера асинхронного порта, но эта скорость обратно пропорциональна надежности передачи и расстоянию между компьютерами, связанными по 0-модемному интерфейсу.

Конфигурация большинства последовательных портов является стандартной, однако наиболее широкое распространение получила конфигурация, соответствующая стандарту RS-232. По этому стандарту разъем содержит 25 контактов. (В компьютере IBM PC AT используется 9-ти контактный разъем). Следует отметить, что довольно большое число последовательных портов не поддерживают весь набор сигналов, специфицированных в стандарте RS-232. Некоторые сигналы не поддерживаются в связи с тем, что они не предназначены для использования в таком приложении и служат для других целей; другие не поддерживаются по причине того, что они выпускались в то время, когда стандарт RS-232 еще не существовал вообще или же целью их создания не являлась полная поддержка стандарта RS-232 и они в этом случае включают лишь ограниченный набор сигналов RS-232 . Наиболее общими сигналами стандарта RS-232 являются:

Сигнал

Штырь разъема

Запрос на посылку данных

4

Очистка для посылки

5

Набор данных готов

6

Набор данных завершен

20

Передача данных

2

Прием данных

3

Земля

7

На самом деле сигналов намного больше и это обусловлено тем, что последовательный порт первоначально разрабатывался как устройство поддержки модема. В связи с этим, если порт используется совместно с другими устройствами, то многие из его сигналов просто в этом случае не нужны. Эти сигналы используются для установления протокола аппаратного уровня между модемом и компьютером, если этот компьютер еще не передавал информацию, но уже готов к ее передаче или передача данных от модема к компьютеру еще не осуществлялась.

Ошибка кадрирования (т.е. ошибка, возникающая при передаче порции данных, передаваемой канальным уровнем сетевого взаимодействия) фиксируется в случае, если частоты синхронизирующих импульсов двух портов значительно отличаются друг от друга. Как вы можете догадаться, последовательный порт после того, как он обнаружил стартовый бит, выделяет регистр ввода, который за каждый цикл считывает один бит. Длина этого цикла определяется скоростью передачи данных. Однако время нахождения бита в регистре определяется тактовой частотой системы. Если частота компьютера-приемника недостаточна для покрытия частоты компьютера-источника, то происходит потеря полученного бита (т.к.. регистр занят), в связи с чем и регистрируется ошибка кадрирования (framing error).

Доступ к порту

Последовательным портом компьютеров семейства IBM PC, а также совместимых с ними моделей можно управлять из DOS через BIOS или в обход DOS и BIOS, используя непосредственное управление аппаратными средствами.

Доступ к последовательному порту через DOS не совсем корректен потому, что DOS не позволяет организовать обратной связи с последовательным портом для анализа его текущего состояния и организует лишь слепое чтение и запись данных в порт. К тому же нет возможности использовать систему прерываний DOS.

Доступ и обработку последовательного порта поддерживают четыре специальные функции BIOS. Обработка последовательного порта осуществляется ими с помощью прерывания 14Н. Отметим, что к последовательному порту обычно подключается устройство типа "мышь". Также с ним может работать и принтер, который имеет последовательный интерфейс.

К сожалению, работа через прерывание 14Н возможна только на относительно небольшой скорости передачи данных через последовательный порт (не более 2400 бод), поскольку BIOS реализует простые опросные алгоритмы работы с аппаратурой последовательного ввода/вывода. Поэтому при работе на больших скоростях с помощью BIOS "обеспечена" потеря данных. Для работы в более скоростном режиме необходима прямая работа с оборудованием.

Далее следует описание адресов портов ввода/вывода, смысла и формата информации, используемой при работе с контроллером последовательного обмена UART 8251.

BIOS инициализирует первые 2 или 4 асинхронных порта. Их базовые адреса располагаются в области данных BIOS, начинающейся с адреса 0000:0400h.

Первый асинхронный порт COM1 имеет базовый адрес 3F8h и занимает диапазон адресов для 10 программируемых однобайтовых регистров от 3F8h до 3FFh.

Асинхронный порт

Базовый адрес

Диапазон адресов

COM2

2F8

2F8 - 2FF

COM3

3E8

3E8 – 3EE

COM4

2E8

2E8 – 2EF

СОМ1, использует IRQ4, обрабатываемое как программное прерывание ОСh.

COM2, использует IRQ3 обрабатываемое как программное прерывание OBh.

Регистры для COM1 и соответствующие им порты ввода/вывода:

3F8 (бит 7 (DLAB)=0 в 3FB) Запись: Регистр данных передатчика.

3F8 (DLAB =0) Чтение: Регистр данных приемника.

3F8 (DLAB =1) Запись: Младший делитель скорости обмена.

3F9 (DLAB =1) Запись: Старший делитель скорости обмена.

3F9 (DLAB =0) Регистр разрешения прерывания.

3FA Регистр идентификации прерывания.

3FB Регистр управления (контроля) линии.

3FC Регистр управления (контроля) модемом.

3FD Регистр статуса линии.

3FE Регистр статуса модема.

 

Для других асинхронных последовательных адаптеров COM Х регистры распределяются на диапазон адресов портов ввода/вывода аналогично, но по своему базовому адресу.

3F8H

DLAB =0: Запись: до 8 бит данных для передачи.

Чтение: до 8 бит принятых данных.

DLAB =1: Запись: младший байт делителя частоты.

После команды OUT 3FBH, 80Н этот регистр должен содержать младший байт делителя частоты, который вместе со старшим байтом (порт 3F9H) содержит 16-битовое число, устанавливающее делитель частоты тактового генератора, от которого в обратно пропорциональной зависимости находится скорость обмена (см. табл.). Делитель скорости обмена – число, на которое надо разделить частоту системных часов (1190.000 Гц) чтобы получить желаемую скорость обмена.

Скорость обмена (бод)

3F9H

3F8H

110

04h

17h

300

01h

80h

600

00h

C0h

1200

00h

60h

1800

00h

40h

2400

00h

30h

3600

00h

20h

4800

00h

18h

9600

00h

0Ch

3F9H

DLAB =1: Запись: старший байт делителя частоты.

DLAB =0: Запись: Регистр управления (разрешения) прерывания

Биты

Описание

0

=1 – Разрешение прерывания при готовности принимаемых данных (при получении данных)

1

=1 – Разрешение прерывания после передачи байта(когда выходной буфер передачи пуст)

2

=1 – Разрешение прерывания по обнаружению состояния BREAK или по ошибке приема данных.

3

=1 – Разрешение прерывания по изменению состояния входных линий на разъеме RS-232–С (C T S, R I , DCD, DSR) (при изменении регистра статуса модема.)

4-7

Должны быть = 0

3FAH

Чтение: регистр идентификации прерываний.

Когда происходит прерывание в этом регистре, можно найти информацию, объясняющую, что же произошло:

Биты

Описание

0

=1 – Нет прерываний, ожидающих обслуживания

1 -2

=00 - прерывание на линии получателя. Появляется в случаях: переполнения, ошибки четности или кадровки, или обрыва линии ( BREAK ), флаг очищается с помощью чтения статуса линии (порт 3FDH)

=01 - полученные данные доступны, флаг очищается с помощью чтения буфера получения (порт 3F8H)

=10 - буфер обмена пуст, флаг очищается при записи в буфер обмена (порт 3F8H)

=11 - Состояние модема. Устанавливается при изменении состояния входных линий CTS, RI, DCD, DSR. Сбрасывается после чтения состояния модема из регистра состояния модема (порт 3FEH).

3-7

Должны быть = 0

3FBH

Чтение/Запись: регистр управления линией

Биты

Описание

0-1

Данные биты определяют длину передаваемых слов в битах (длина символа):

=00 – 5 бит

=01 – 6 бит

=10 – 7 бит

=11 – 8 бит

2

Количество стоповых бит:

=0 - 1

=1 - 1,5 ,если длина символов равна 5

=1 - 2

3-4

Четность (не используется BIOS ):

=х0 – контроль на четность не выполняется.

=01 – выполняется проверка на нечетность.

=11 – выполняется проверка на четность.

5

Фиксация четности. При установке этого бита, бит четности всегда принимает значения 0 (если биты 3-4 равны 11) или 1 (если биты 3 -4 равны 01)

6

Установка перерыва. Вызывает вывод строки нулей в качестве сигнала отдаленной станции(BREAK для подключенного устройства)

=1 - начать посылать цепочку нулей

7

DLAB ( Divisor Latch Access Bit ) Меняет адреса портов других регистров. Бит используется для доступа к регистру установки скорости.

=1 - регистр данных и регистр управления прерываниями используются для загрузки делителя частоты тактового генератора.

=0 - регистр данных и регистр управления прерываниями используются как обычно.

 

3FCH

Запись: регистр управления модемом

Биты

Описание

0

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

=1 - “готовность компьютера” активна.

1

Линия RTS . Сигнал подтверждения связи

=1 - “Запрос на посылку” активен

2

Линия OUT1 (запасная). Для некоторых модемов при установке этого бита в 1 происходит его аппаратный сброс.

Добав пользователь назначен на вывод #1

3

Линия OUT2 (запасная )

=1 – UART может вырабатывать прерывания

=0 – не может

4

Запуск диагностики при входе асинхронного адаптера, замкнутом на его выход (Digital Loopback test). Эта возможность реализована только для асинхронных портов, использующих UART 8250

=1 - активна токовая петля для диагностики (внутренний шлейф)

5-7

Должны быть равны 0

 

3FDH

Чтение: регистр состояния (статуса) линии

Биты

Описание

0

=1 - готовность данных (DR). Данные получены и готовы для чтения, при чтении данных из регистра данных приемника (3F8) бит сбрасывается.

1

=1 – ошибка переполнения (ОЕ). Был принят новый байт данных, а предыдущий не считан. В результате предыдущий байт потерян.

2

=1 - ошибка паритета (четности) (РЕ). Очищается чтением статуса линии.

3

=1 - ошибка кадра (FE). Плохой стоп-бит, нарушение синхронизации посылки.

4

=1 - индикация обрыва (BI). Обнаружен перерыв (запрос на прерывание передачи BREAK) – длинная строка нулей, инициализирующая что другая станция запрашивает конец передачи.

5

=1 - регистр хранения передатчика пуст, в него можно записывать новый байт для передачи.

6

=1 - регистр сдвига передатчика пуст . Этот регистр получает данные из регистра хранения и преобразует из в последовательный вид для передачи. Если этот бит равен единице, то UART может принять очередной символ от компьютера.

7

=1 - тайм–аут (Устройство не связано с компьютером).

Примечание: любой из битов 1-4 вызывает прерывание, если оно разрешено (см. порт 3F9H)

3FEH

Чтение: регистр состояния (статуса) модема

Биты

Описание

0

=1 - изменено состояние Delta Clear To Send (DCTS).

1

=1 - изменено состояние Delta Data Set Ready ( DDSR ).

2

=1 - активен Trailing Edge Ring Indicator (TERI), изменено состояние RI.

3

=1 - изменено состояние Delta Data Carrier Detect (DDCD).

4

=1 - активен Clear To Send (CTS).

5

=1 - активен Data Set Ready (DSR).

6

=1 - индикатор звонка (Ring Indicator -RI).

7

=1 - есть несущая (Data Carrier Detect -DCD).

Примечание. Любой из битов 0-3 может вызывать прерывание, если оно разрешено (см. порт 3F9H)

В заключение отметим, что при программировании аппаратуры последовательного порта необходимо помнить, что контроллеру прерываний необходимо сообщать о завершении обработки соответствующего прерывания, посылая в порт 20h универсальный сигнал о завершении обработки прерывания 20h.

Пример 1 : два компьютера соединены 0-модемным кабелем через последовательные порты (COM1-->COM1). Необходимо реализовать передачу байтов между компьютерами по опросу готовности последовательного порта. При приеме символа, соответствующего клавише [Tab], приемник завершает работу. Передатчик завершает свою работу по нажатию клавиши [Esc].

Формат кадра: количество информационных бит = 8,

количество стоповых бит = 2,

контроль четности отсутствует.

 

up