Вопрос

У меня есть рабочее соединение с моим последовательным устройством через Pyserial, но я также хочу перенести файлы через протокол Xmodem в рамках моей программы.

Что было бы наиболее нейтральным платформой, чтобы сделать это? В худшем случае я мог close() мой serial.Serial объект в питоне и использовать subprocess призывать /usr/bin/sb, но это кажется неэлегантным.

В настоящее время я нахожусь на Ubuntu 9.10 и использую адаптер USB-TTY.

Любые идеи?

Это было полезно?

Решение

На PYPI есть модуль Xmodem. Требуется две функции в конструкторе для чтения и написания данных, реализуйте их для работы с вашим открытым последовательным портом. Ниже проста его использования:

import serial
try:
    from cStringIO import StringIO
except:
    from StringIO import StringIO
from xmodem import XMODEM, CRC
from time import sleep

def readUntil(char = None):
    def serialPortReader():
        while True:
            tmp = port.read(1)
            if not tmp or (char and char == tmp):
                break
            yield tmp
    return ''.join(serialPortReader())

def getc(size, timeout=1):
    return port.read(size)

def putc(data, timeout=1):
    port.write(data)
    sleep(0.001) # give device time to send ACK


port = serial.Serial(port='COM5',parity=serial.PARITY_NONE,bytesize=serial.EIGHTBITS,stopbits=serial.STOPBITS_ONE,timeout=0,xonxoff=0,rtscts=0,dsrdtr=0,baudrate=115200)
port.write("command that loads data via xmodem\r\n")
sleep(0.02) # give device time to handle command
readUntil(CRC)
buffer = StringIO('data to send')
XMODEM(getc, putc).send(buffer, quiet = 1)
buffer.close()
readUntil()

Другие советы

Супер просто использовать реализацию протокола Xmodem, найденную на PYPI. Несколько вещей, на которые следует отметить пример выше, это то, что есть некоторые вещи, которые не нужны. (Может быть, это сработало для автора или с предыдущей версией модуля?)

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

import serial
from xmodem import XMODEM

ser = serial.Serial(port='COM56')


def getc(size, timeout=8):
    gbytes = ser.read(size)
    print(f'Read Byte: {gbytes}')
    return gbytes or None


def putc(data, timeout=8):
    pbytes = ser.write(data)
    print(f'Put Byte: {pbytes}')
    return pbytes or None


if __name__ == '__main__':
    modem = XMODEM(getc, putc)

Получить с серийного устройства:

stream = open('output', 'wb')
modem.recv(stream, crc_mode=0)

Отправить на серийное устройство:

stream = open('input', 'rb')
modem.send(stream)

Ключ здесь состоит в том, чтобы убедиться, что скорость передачи передачи задач с обеих сторон (здесь не дефолт). Не добавляйте никакой задержки или сна, так как это не основано на времени, а на транзакции. Отпечатки позволят вам увидеть транзакцию в реальном времени, когда данные течет в файле/последовательном порту или выходят из файла.

Я не знаком с деталями протокола Xmodem, но один человек отвечает Xmodem-for-Python Вопрос, по -видимому, и даже предоставил то, что похоже на грубую реализацию Xmodem в Питон. Возможно, вы могли бы использовать это или идеи из других ответов там.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top