2013-03-21 2 views
2

Я как отправить некоторые команды микроконтроллеру LPC 1786 через последовательный порт. Для выполнения этой задачи я открываю последовательный порт, используя этот код.Последовательная связь с LPC1786

struct termios tio; 
int tty_fd; 

memset(&tio,0,sizeof(tio)); 
tio.c_iflag = 0; 
tio.c_oflag = 0; 
tio.c_cflag = CS8|CREAD|CLOCAL;   // 8n1, see termios.h for more information 
tio.c_lflag = 0; 
tio.c_cc[VMIN] = 1; 
tio.c_cc[VTIME] = 5; 

tty_fd = open(device, O_RDWR | O_NONBLOCK); 
cfsetospeed(&tio, B9600);   // 115200 baud 
cfsetispeed(&tio, B9600);   // 115200 baud 
tcflush(tty_fd, TCIFLUSH); 

Это для встроенной системы Linux, использующей (iMX53). Когда я компилирую код на своем ПК и запускаю его. Я получаю это:

sent: ? 
recieve: Sinchronized<CR><LF> 
sent: Sinchronized<CR><LF> 
recieve: Synchronized<CR>OK<CR><LF> 
sent: 16000<CR><LF> 
recieve: 16000<CR>OK<CR><LF> 

ведьма в порядке. Когда я переписываю его и загружаю в систему, я получаю это.

Sent: ? 
HEX: 0x53 0x79 0x6E 0x63 0x68 0x72 0x6F 0x6E 0x69 0x7A 0x65 0x64 0xA 0xA 0x53 0x79 0x6E 0x63 0x68 0x72 0x6F 0x6E 0x69 0x7A 0x65 0xA 
ASCII: SynchronizedSynchronizedOKOKnchronized1K024K024chronized1 

Sent: ? 
HEX: 0xA 0xA 0xA 0xA 0xA 0xA 0xA 0x30 0xA 0xA 0x31 0xA 0xA 0xA 0xA 0xA 0xA 0x34 0xA 0xA 0x31 0xA 0xA 0xA 0xA 0xA 0xA 0xA 0xA 0xA 0A 
ASCII: 014141hronized1111111ronized1 

ведьма вид руин мой день. Для записи и чтения я использую функции чтения &. Я уверен, что это связано с тем, как я открываю последовательный порт. Но что случилось. Я пробовал разные настройки, но с небольшим успехом. В лучшем случае в качестве ответа я получаю «????? 1 ???». И большую часть времени читать нечего.

+2

В какой скорости вы работаете? Такие проблемы всегда пахнут несоответствиями скорости передачи. Я вижу 9600 в вашем коде, 115200 в комментарии и понятия не имею, что это на стороне хоста: P – slugonamission

+0

Я тестировал разные скорости. хост -> скорость 9600 бод; stty:/dev/ttymxc4 intr =^C; quit =^\; erase =^?; kill =^U; eof =^D; eol = ; eol2 = ; start =^Q; stop =^S; susp =^Z; rprnt =^R; werase =^W; lnext =^V; flush =^O; min = 1; time = 0; -parenb -parodd cs8 HUPCL -cstopb CREAD CLOCAL -crtscts -ignbrk -brkint -ignpar -parmrk -inpck -istrip -inlcr -igncr ICRNL IXON -ixoff -iuclc -ixany -imaxbel OPOST -olcuc -ocrnl ONLCR -onocr -onlret -ofill -ofdel nl0 cr0 tab0 bs0 vt0 ff0 isig icanon iexten echo echoe echok -echonl -noflsh -xcase -tostop -echoprt echoctl echoke – DimDqkov

+0

Это странно. Вы уверены, что входные часы вашего процессора верны? – slugonamission

ответ

3

Фундаментальной проблема заключается в том, что ваш код указывает, что у вас нет (правильно) инициализирован порт tty. По сути, инициализация не вызывает tcsetattr(), чтобы установить обновленную конфигурацию, которую вы пытались указать.

Правильный способ инициализации порта tty - открыть порт, получить текущие атрибуты, сохранить текущие атрибуты для восстановления при выходе из программы, изменить атрибуты и установить атрибуты. И всегда проверяйте коды возврата из системных вызовов.

tty_fd = open(device, O_RDWR | O_NONBLOCK); 
    if (tty_fd< 0) { 
     syslog(LOG_DEBUG, "failed to open: %d, %s", tty_fd, strerror(errno)); 
     exit (-1); 
    } 
    rc = tcgetattr(tty_fd, &tio); 
    if (rc < 0) { 
     syslog(LOG_DEBUG, "failed to get attr: %d, %s", rc, strerror(errno)); 
     exit (-2); 
    } 
    savetio = tio; /* preserve original settings for restoration */ 

    spd = B9600; 
    cfsetospeed(&tio, (speed_t)spd); 
    cfsetispeed(&tio, (speed_t)spd); 

    cfmakeraw(&tio); 

    tio.c_cc[VMIN] = 1; 
    tio.c_cc[VTIME] = 5; 

    tio.c_cflag &= ~CSTOPB; 
    tio.c_cflag &= ~CRTSCTS; /* no HW flow control? */ 
    tio.c_cflag |= CLOCAL | CREAD; 
    rc = tcsetattr(tty_fd, TCSANOW, &tio); 
    if (rc < 0) { 
     syslog(LOG_DEBUG, "failed to set attr: %d, %s", rc, strerror(errno)); 
     exit (-3); 
    } 

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

Вот руководство по programming the serial port.

+0

Не назвав tcsetattr главной проблемой. Я прошел через гид и внедрил некоторые изменения. Я чувствую себя довольно глупо ... сколько времени я потратил на этот грирр. Теперь он работает нормально. Спасибо. – DimDqkov

1

Там очень много хороших комментарии отладки на этот вопрос, но вот аннотированный список предметов для проверки последовательной связи: (Добавление некоторых из моих собственных & наклонных по отношению к воспитанию систем развития)

Этих два это своего рода начальные проверки уровня проекта. Иногда вы в конечном итоге пересматриваете их:

  • Проверьте технические данные: соответствуют ли уровни напряжения? например, «True» RS232 vs TTL, 12v vs 5v vs 3v
  • Выключите кабельные или цепные соединения: заземление, rx переходит в tx, если дифференциальный TX +/TX- и т. д. соответствует? (Особенно, если это заказ или ручной сборки кабеля)

Это более общий:

  • Убедитесь, что скорость передачи данных соответствует
  • Проверьте данные, стоп-биты и потока настройки управления совпадают на оба конца
  • Работает ли более низкая скорость передачи данных?
  • Возможно, попробуйте альтернативные кабели?
  • Возможно, попробуйте другой компьютер (если у вас был нечетный контур заземления с источником переменного тока для ноутбука)
  • Сделайте, если возможно, один конец «известным хорошим» количеством.

Эти редкие проверки:

  • Проверьте любые настройки входного тактового питающие скорость передачи данных последовательного периферийного устройства.
  • вспыхнуть рамки и посмотреть, чтобы увидеть, если сигнал поврежденные (как «квадрат» ваши изменения уровня и они соответствуют тому, что вы думаете, что уровни напряжения вашего оборудования являются)
1

В дополнение к проблемам, упомянутым в другом ответе, одна из вероятных причин - это плохие часы предварительного масштабирования, подаваемые на MCU UART. UART требует точности часов + - 3%. Если ваш предварительный сканер не так точен, вы точно определите 0-вид вопросов, описанных в вопросе: данные отлично смотрятся в большинстве случаев, а затем вдруг вы получаете мусор.

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

1

Я аппаратный парень в сердце, так что, когда такие вещи, как это произойдет, я, как правило, начинается с нижней:

  • Получить объем или логический анализатор, и смотреть на переданных битов. Проверьте скорость передачи в бодах. Проверьте символы. Область, которая интерпретирует биты для вас, представляет собой огромную помощь здесь :)

  • Если они в порядке, проверьте, что байты попадают во встроенный процессор. Проверьте процедуру обслуживания прерываний. Установите бит на запись и очистите его перед выходом. Убедитесь, что входящие символы не перекрывают ISR.

Работайте оттуда - есть ли драйвер низкого уровня, берущий данные из ISR?

+0

Это очень хороший совет. И это то, что сделал один из моих старших коллег, когда я рассказал ему о проблеме. – DimDqkov