/dev/mem или пакетная передача пользовательского пространства; как получить более быстрый доступ к /dev/mem

настройка

У меня есть куча оперативной памяти на стороне PL (программируемая логика / FPGA) чипа zync-7000. Доступ к этой памяти возможен как со стороны PL, так и со стороны PS (система обработки/ЦП). План состоит в том, чтобы ЦП загружал большой буфер GiB и передал его PL.

Linux загружается в оперативную память и из нее при изменении дерева устройств

Когда я изменяю дерево устройств, чтобы Linux мог видеть оперативную память, я наблюдаю высокую скорость чтения/записи; аппаратное/микропрограммное обеспечение поддерживает пакетное чтение/запись.

    memory {
        device_type = "memory";
        // The 512 MiB memory at 0x60000000
        reg = <0x0 0x40000000 0x60000000 0x20000000>;
    };

mmap память дерева устройств

Дерево устройств изменено, чтобы линукс не использовал ОЗУ (вместо этого его можно использовать в качестве буфера для PL)

    memory {
        device_type = "memory";
        reg = <0x0 0x40000000>;
    };

mmap работает медленно даже после игры с флагами

Я пробовал несколько способов настройки mmap()

int* addr_start = mmap(NULL, mmap_size, PROT_READ | PROT_WRITE, MAP_SHARED, fd, address);
int* addr_start = mmap(NULL, mmap_size, PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_POPULATE, fd, address);

Хотя они надежны, ни один из них не дает быстрых результатов при выполнении итерации — теста записи/чтения.

// words_per_page is on the order of 2**20/4
case TEST_WRITE:
    for( int ii=0; ii < words_per_page; ii++)
        *waddr++=count++;
    break;
case TEST_READ:
    for( int ii=0; ii < words_per_page; ii++)
        sum += *raddr++;
    break;

вопрос

Существуют ли какие-либо способы создания прямых пакетных транзакций в/из памяти в пользовательском пространстве? Если нет, будут оценены соответствующие ссылки на ядро ​​​​Linux.


person philn    schedule 01.11.2020    source источник
comment
Какой это язык? Я предполагаю, что это C, кажется   -  person new QOpenGLWidget    schedule 01.11.2020
comment
Когда ОЗУ объявлено как системная память, доступ к этой памяти будет осуществляться с использованием кеша процессора, т. е. кэширования чтения и обратной записи. Для ОЗУ, которое используется для ввода-вывода и/или совместного использования, обычно требуется, чтобы эта область памяти не кэшировалась, чтобы избежать проблем с когерентностью.   -  person sawdust    schedule 02.11.2020
comment
@zixuan Да, я пишу это на C для низкоуровневого доступа   -  person philn    schedule 02.11.2020
comment
@sawdust В этом есть смысл, но есть ли способ кэшировать память и время от времени очищать ее?   -  person philn    schedule 02.11.2020
comment
Есть ли способ кэшировать память и время от времени сбрасывать ее? -- Да, из ядра Linux; см. kernel.org/doc/gorman/html/understand/understand006. .html#toc26. Но если нет синхронизации с другим процессором (процессорами), существует риск возникновения условий гонки и, как следствие, проблем с когерентностью.   -  person sawdust    schedule 02.11.2020


Ответы (1)


Вам определенно нужно отобразить область как буферную, чтобы максимизировать скорость передачи. Возможно, вам потребуется использовать драйвер устройства, отличный от /dev/mem.

Управлять передачей со стороны программируемой логики проще, если вы используете DMA в память хоста Zynq. В Zynq я обнаружил, что мне нужно 8 запросов на чтение максимальной длины в полете за раз, чтобы максимизировать пропускную способность по ссылке.

Если вам нужна согласованность кеша с пользовательским пространством, вам нужно будет использовать порт ACP, чтобы кеш процессора отслеживал записи в память из программируемой логики (PL).

person Jamey Hicks    schedule 05.12.2020