Помощь - Поиск - Пользователи - Календарь
Полная версия этой страницы: CY7C680013A Киньте ссылкой на софт и лит-ру
Форум разработчиков электроники ELECTRONIX.ru > Интерфейсы > Форумы по интерфейсам > RS232/LPT/USB/PCMCIA/FireWire
Страницы: 1, 2
-=Vitaly=-
С Новым Годом!!!
Здравствуйте премногоуважаемые жители форума!!!

Имею сей контроллер не знаю как к нему подступиться чтобы USB начаеть делать. Какой софт юзать??
Смотрел кейл, там вроде этот проц есть. Может есть что специфическое от cypressa??
А для разработки драйвера и софта под виндой че юзать???

СПС!!!
aaarrr
Для начала стоит посмотреть софт от developer kit'а, там как раз Keil и используется в качестве компилятора, есть примеры.
Простой поиск на сайте Cypress'а CY7C68013A (только с правильным количеством нулей) дает кучу ссылок.
rvk
Для того, чтобы полностью врубиться в USB стандарт, а также
написать программу под этот чип в Keil и спроектировать схему
нужен всего один документ : FX2 TechRefManual.pdf, он лежит
в разделе доков для данного чипа на сайте Cypress.
По поводу драйвера :
Можно воспользоваться уже готовым драйвером с исходниками EZUSB.sys, к нему же в ките, который лежит там же, в разделе SDK для чипа на сайте cypress, есть программа под винду, которая работает в паре с драйвером, тоже с исходниками.
Если не нравится EZUSB, он слегка тормознутый, можно использовать
драйвер CyUSB.sys, тоже есть с исходниками.
Правда верхняя программа под него, классная кстати идет уже без сорцов.
Можно воспользоваться уловкой виндов и использовать свое устройство как MASS STORAGE DEVICE, что значит, чип обзывает себя накопителем, как это делается смотреть на сайте usb.org,
ссылки в это форуме есть. Тогда драйвер не нужен в принципе,
используется готовый по умолчанию в виндах.
Ну а если очень хочется можно написать свой с нуля с помощью WIN XP DDK.
Ну и конечно понадобится собственно USB2.0 спецификация, там же на usb.org.
-=Vitaly=-
Спасибо, я где-то так и делал. Просто для подстраховки, чтобы не забыть чего-то!!!
jur
Цитата(rvk @ Jan 2 2007, 14:29) *
можно использовать драйвер CyUSB.sys, тоже есть с исходниками.
Я использую этот драйвер. Отлично работает! Хотел поинтересоваться, а где его исходники найти? А то в китах все больше EZUSB.sys приводится.
rvk
Да извините прогнал я по поводу CyUSB, исходников нет, есть
только API файл с заголовком и библиотекой для использования
в программе верхнего уровня.
XShocK
FX2_TechRefManual.pdf + GPIF_Primer.pdf рулят. Только в последнем они постоянно что-то недоговаривают. Во всяком случае мне все время так кажется.

А я вот просидел 3 дня, прикрутил его родимого к Spartan 3, пакеты летают по GPIF как ласточки. Но вот на комп(возможно и на сам спартан тоже) отдельные пакетики в 512 байт прилетают как попало. Было-бы очень интересно как правильно решать такую проблему.
jur
Цитата(rvk @ Jan 2 2007, 19:17) *
Да извините прогнал я по поводу CyUSB, исходников нет
Ну вот... А я уже губки раскатал... :-)

Цитата(XShocK @ Jan 3 2007, 05:51) *
FX2_TechRefManual.pdf + GPIF_Primer.pdf рулят. Только в последнем они постоянно что-то недоговаривают. Во всяком случае мне все время так кажется.
Есть такая буква... Но вообще-то этот Primer - хороший материал. Он даже в основу хелпа GPIF Designer'а лёг. Правда, я не смог с их дурацкого сайта (ох, прошелся бы я серпом по избранным местам их web-дезайнера!) скачать исходники: нажимаю линк - ничего не скачивается (скачал только сам PDF с описанием). Пришлось обращаться в техподдержку, они мне приаттачили ZIP-архив с этими исходниками.

Цитата(XShocK @ Jan 3 2007, 05:51) *
А я вот просидел 3 дня, прикрутил его родимого к Spartan 3, пакеты летают по GPIF как ласточки. Но вот на комп (возможно и на сам спартан тоже) отдельные пакетики в 512 байт прилетают как попало. Было-бы очень интересно как правильно решать такую проблему.
Не знаю, что используется на компьютерной стороне, но я пользуюсь CyAPI к их превосходному CyUSB.sys. У меня была похожая проблема, пакеты хаотически не приходили. Понятное дело, грешил на их драйвер. Но зря. Оказалось, что в моем железе была трудноуловимая ошибка, импульс SLWR изредка был короче, чем нужно (речь о CY7C68001). Поэтому мне думается, что если работа идет через CyAPI, то желательно очень внимательно проверить железо. В Спартане что-нибудь отладочное намутить, хотя бы пакеты подсчитывать. Т.к. их CyAPI работает очень хорошо, я на него грешил бы в последнюю очередь.
XShocK
Цитата(jur @ Jan 3 2007, 09:36) *
Не знаю, что используется на компьютерной стороне, но я пользуюсь CyAPI к их превосходному CyUSB.sys. У меня была похожая проблема, пакеты хаотически не приходили. Понятное дело, грешил на их драйвер. Но зря. Оказалось, что в моем железе была трудноуловимая ошибка, импульс SLWR изредка был короче, чем нужно (речь о CY7C68001). Поэтому мне думается, что если работа идет через CyAPI, то желательно очень внимательно проверить железо. В Спартане что-нибудь отладочное намутить, хотя бы пакеты подсчитывать. Т.к. их CyAPI работает очень хорошо, я на него грешил бы в последнюю очередь.


Я наверно выразился немного смутно. Все пакеты приходят, и насколько я понял без ошибок. Проблема в том, что эти самые пакеты приходят не в правильном порядке. Если отправление делать медленно, то все путем. Стоит начать отправлять без задержки, так начинаются проблемы. На компе запущен CyBulk(та, что идет в пакете sdk) который и проверяет целостность. Насколько я понимаю USB в Bulk режиме не дает гарантии когда пакет придет, но я так и не понял, что насчет гарантии очередности пакетов. Если ее нет то посоветуйте, как правильно и быстро(что важно) это можно решить.
XShocK
Мой вопрос отпадает. Написал свою прогу на CyAPI и все начало работать. Видать этот CyBulk как-то странно считывает данные.
Теперь правда беда, скорость с CyAPI ник черту. Видео 512 на 512 8-бит идет всего 25 фпс, это примерно 12 мегабайт/сек. А хочется 35 мб/сек.
grumbler
Цитата(XShocK @ Jan 4 2007, 06:16) *
Мой вопрос отпадает. Написал свою прогу на CyAPI и все начало работать. Видать этот CyBulk как-то странно считывает данные.
Теперь правда беда, скорость с CyAPI ник черту. Видео 512 на 512 8-бит идет всего 25 фпс, это примерно 12 мегабайт/сек. А хочется 35 мб/сек.

Забить на CyAPI - перейти на USBIO и всё получится. А как провереяте скорость ? Переполнение буферов ?
XShocK
Цитата(grumbler @ Jan 4 2007, 06:20) *
Забить на CyAPI - перейти на USBIO и всё получится. А как провереяте скорость ? Переполнение буферов ?


Программа посылает Спартану картинку, тот ее по простому инвертирует и отсылает назад, на моем конце я гляжу частоту с которой я принимаю кадры. Судя по этому и расчитал, что примерно 12 метров.
Насчет переполнения буферов. Судя по мигающему на борде светодиоду ПЛИС справляется со своим делом очень быстро. Почти все время стоит в ожидании. Я поставил на вход и на выход по 2кб фифо, так что и ПЛИС микроконтроллер помоему не стоят.
Еще я попробовал убрать весь код какой можно было из главного цикла. Скорость поднялась с 25 до 27 кадров с сек.
Так что последую вашему совету и попробую USBIO.
grumbler
Программа посылает Спартану картинку, тот ее по простому инвертирует и отсылает назад, на моем конце я гляжу частоту с которой я принимаю кадры. Судя по этому и расчитал, что примерно 12 метров.
Насчет переполнения буферов. Судя по мигающему на борде светодиоду ПЛИС справляется со своим делом очень быстро. Почти все время стоит в ожидании. Я поставил на вход и на выход по 2кб фифо, так что и ПЛИС микроконтроллер помоему не стоят.

А какого размера буфер софтовый передается драйверу ? Размером на кадр или маленький ?
Еще я попробовал убрать весь код какой можно было из главного цикла. Скорость поднялась с 25 до 27 кадров с сек.
Какая машина используется ?
Так что последую вашему совету и попробую USBIO.
У нас когда то давно получилось на ввод получить примерно 27Мб, больше не было потребности.
XShocK
Цитата(grumbler @ Jan 4 2007, 07:14) *
А какого размера буфер софтовый передается драйверу ? Размером на кадр или маленький ?

Размер буфера на весь кадр, тоесть примерно 260 кбайт.

Цитата(grumbler @ Jan 4 2007, 07:14) *
Какая машина используется ?

Pentium 4 3.06ghz, 533 mhz bus. Мать с 865 чипсетом.

Только что попробовал USBIO Demo application и его
Read File to Pipe и второй с Write Pipe to File. Тоесть
пишу в EP2OUT и читаю из EP6IN.
При запуске оба показывают стабильно 8.9 мегабайт/с. Тоесть
примерно 18 мбайт/с так как трафик идет в обе стороны.
Уже не 12 как в CyAPI, но и не желаемые 30-35.
jur
Цитата(grumbler @ Jan 4 2007, 06:20) *
Забить на CyAPI - перейти на USBIO и всё получится.
Ну не знаю, не знаю... По моему, от API это никак не зависит, все дело в драйвере. А драйверу все равно, как к нему обращаться: посредством своих низкоуровневых вызовов, или через CyAPI. Является ли драйвер ezusb.sys лучше чем CyUSB.sys я тоже затрудняюсь сказать. Во всяком случае специалисты самой Cypress говорят, что предпочтительнее использовать CyUSB.sys. Кроме того, ничто не мешает работать с CyUSB.sys посредством низкоуровневых вызовов, т.к. хендл драйвера всегда имеется (вызов DeviceHandle).

Что касается CyAPI, то нужно помнить, что для скоростного обмена данными следует использовать асинхронный ввод/вывод через связку BeginDataXfer->WaitForXfer->FinishDataXfer, а не простой XferData. Также следует учесть буферирование. Например, для своих скоростей передачи (до 8 МБ) я опытным путем выяснил, что достаточная скорость достигается при очереди из 4 запросов по 8 512-байтных блоков в каждом (увеличение до 16-ти или 32-х увеличивает общую скорость передачи, но уже не намного). Далее. Передача данных должна обязательно производиться в отдельном треде, для которого нужно выставить повышенный приоритет (я выставляю THREAD_PRIORITY_TIME_CRITICAL).

Ну и, наконец, достижение скоростей передачи в 30-35 МБ/сек - далеко не тривиальная задача! Достаточно взглянуть на скорость передачи данных с одного винчестера на другой. У меня скорость такой передачи на дисках EIDE даже 30 МБ не достигает! А ведь эта процедура выполняется системными средствами, хорошо вылизанными и отлаженными системными драйверами! Получить скорость более 35 МБ удается только с дисками SATA. Поэтому мне думается, что задача достижения скорости передачи в 30-35 МБ/сек должна решаться комплексно, с учетом не только драйверного хозяйства, но и приложения, использующего эти данные. Кстати, очень полезно провести хронометраж с помощью точного таймера (того, который QueryPerformanceCounter), это может помочь выявить узкие места.
jur
Цитата(XShocK @ Jan 4 2007, 06:16) *
Теперь правда беда, скорость с CyAPI ни к черту. Видео 512 на 512 8-бит идет всего 25 фпс, это примерно 12 мегабайт/сек. А хочется 35 мб/сек.
Да, кстати, у меня точно такой же размер видеокартинки, тоже 512 на 512 8-бит. Передача исходных 8-битных данных по USB, конвертация в 32-бит и отображение картинки на экране легко укладывается в ~20-25 msec, т.е. 40-50 FPS. А частота 25 FPS при размере картинки четверть мегабайта дают не 12, а чуть больше 6-ти мегабайт/сек ;-) Это, на самом деле, как-то маловато... Подозреваю, что передача данных производится посредством XferData...
-=Vitaly=-
Мне надо 50-60 мб/cек. GPIF работает в режиме SLAVE на 48 мГц 16 бит, смогу ли достичть заданной скорости???

И какую предельную скорость выжимали из этого проца????
blink.gif blink.gif
jur
Цитата(-=Vitaly=- @ Jan 4 2007, 12:40) *
Мне надо 50-60 мб/cек. GPIF работает в режиме SLAVE на 48 мГц 16 бит, смогу ли достичть заданной скорости???
И какую предельную скорость выжимали из этого проца????
Из этой микросхемы реально выжимается скорость в 96 МБ/сек (см. GPIF Primer). А возможно ли ее достичь? Хм... Смотря в каком приложении, на каком компьютере, под какой операционной системой и насколько длительно. Небольшими порциями (пачками по несколько пакетов), наверное, вполне возможно.
-=Vitaly=-
Ладно сделаем посмотрим.
Еще вопрос, в режиме SLAVE пакет готов к передачи по USB, когда я полностью заполнил буфер или дернул PKTEND для короткого пакета???
XShocK
Цитата(jur @ Jan 4 2007, 10:20) *
Цитата(XShocK @ Jan 4 2007, 06:16) *
Теперь правда беда, скорость с CyAPI ни к черту. Видео 512 на 512 8-бит идет всего 25 фпс, это примерно 12 мегабайт/сек. А хочется 35 мб/сек.
Да, кстати, у меня точно такой же размер видеокартинки, тоже 512 на 512 8-бит. Передача исходных 8-битных данных по USB, конвертация в 32-бит и отображение картинки на экране легко укладывается в ~20-25 msec, т.е. 40-50 FPS. А частота 25 FPS при размере картинки четверть мегабайта дают не 12, а чуть больше 6-ти мегабайт/сек ;-) Это, на самом деле, как-то маловато... Подозреваю, что передача данных производится посредством XferData...


Да. Получается 6 мегабаит/сек, но только в одну сторону, а я пишу 6 мегабаит и тут-же считиваю теже 6 мегабаит обратно. Так и получаю 12. Использую асинхронную передачу, тоесть OutEndpoint->BeginXTransfer; InEndpoint->BeginXTransfer; Wait; Finish. Отдельный тред использовать не пробовал. Сегодня попробую, но боюсь это даст мало ускорения.
jur
Цитата(-=Vitaly=- @ Jan 4 2007, 14:09) *
Еще вопрос, в режиме SLAVE пакет готов к передачи по USB, когда я полностью заполнил буфер или дернул PKTEND для короткого пакета???
Пакет уходит в USB, когда он полностью заполнен, т.е. записал 512 байт в ФИФО - пакет ушел (не важно, что ФИФО еще не полностью заполнено). PKTEND нужно дергать только для коротких пакетов, т.е. таких, которые меньше заданного максимального размера пакета (в данном случае 512 байт). По моему так.
Цитата(XShocK @ Jan 4 2007, 14:49) *
Да. Получается 6 мегабаит/сек, но только в одну сторону, а я пишу 6 мегабаит и тут-же считиваю теже 6 мегабаит обратно. Так и получаю 12.
А, теперь понял.
Цитата(XShocK @ Jan 4 2007, 14:49) *
Использую асинхронную передачу, тоесть OutEndpoint->BeginXTransfer; InEndpoint->BeginXTransfer; Wait; Finish. Отдельный тред использовать не пробовал. Сегодня попробую, но боюсь это даст мало ускорения.
Хм... Тогда непонятно... Получается, что необходимо применить точный таймер QueryPerformanceCounter, чтобы выявить узкие места в тракте передачи. Может для начала стоит попробовать просто подсчитывать полученные пакеты, никуда дальше их не передавая? Так можно будет оценить скорость чистой передачи по USB без учета вклада прикладной программы.

P.S. Да, совсем забыл сказать. Насколько я помню, речь идет о передаче всего кадра целиком, всех 256 КБ одним махом? Возможно, проблема кроется именно в этом. Т.е. для Винды, которая никоим образом не ОС РВ, подобные процедуры следует выполнять в виде очереди запросов. Например, у меня запускается четыре запроса по 8 блоков в каждом (можно и побольше блоков взять). Тут ведь нужно помнить, что вызов драйвера - серьезная процедура. Если вызвать считывание 256 КБ, дождаться их прихода и начать что-то делать с полученными данными, то это будет катастрофически расточительное расходование системных ресурсов (времени). Следует нагружать драйвер постоянно. Кстати, именно поэтому совершенно необходимо применять технологию передачи данных в отдельном потоке (треде).
jur
(К моему предыдущему посту. Почему-то не получилось в него вставить.)

P.P.S. Еще. Я как-то сразу не обратил внимание. Ведь передача идет "туда" и считывается "обратно", так? В таком случае высокой скорости добиться невозможно (ну, или очень сложными, нестандартными методами). И все это потому, что, опять же, Винда никаким боком не ОС РВ. В случае такой передачи однозначно нужно применять треды. Т.е. нужно выдавать поток исходных кадров и параллельно считывать обратно поток обработанных кадров. Альтернативный вариант - переписывание драйвера с целью придания ему свойств реалтаймовости. Не думаю, что это просто... Да и совсем не нужно при вдумчивом построении своего приложения на основе тредов.
XShocK
Дело в том, что если использовать оочень большой буфер(5 мегабайт), ничего не меняет. Тоесть скорость падает пропорционально. 3 запроса драйверу в секунду при таком раскладе боюсь большой роли тут не играют. Тут или материнка виновата или я чтото наделал неправильного с прошивкой Сайпреса.

Вот код отправлющий пакеты(выше стоит while(1) handle_fifo_gpif_requests()wink.gif Посмотрите, может я чего не так делаю. Спасибо.

Код
void handle_fifo_gpif_requests() {
  // Handle OUT EP2 host request
  if( GPIFTRIG & 0x80 )  // if GPIF interface IDLE
  {  
    // if there's a packet in the peripheral domain for EP2
    if ( ! ( EP24FIFOFLGS & 0x02 ) )
    {
      if( !is_external_fifo_full() ) {
        Setup_FLOWSTATE_Write(); // setup FLOWSTATE registers for FIFO Write operation
    SYNCDELAY;

REPEAT_WRITE:
    SYNCDELAY;
        GPIFTCB1 = 0x01; //(packet_size / 2) >> 8; // upper nibble of number of bytes / 2-byte wide bus
        SYNCDELAY;
        GPIFTCB0 = 0x00; //(packet_size / 2) & 0xFF; // lower nibble
        SYNCDELAY;
        GPIFTRIG = GPIF_EP2;            // launch GPIF FIFO WRITE Transaction from EP2 FIFO
    SYNCDELAY;

        while( !( GPIFTRIG & 0x80 ) ) // poll GPIFTRIG.7 GPIF Done bit
        {
        ;
        }

        if ( ! ( EP24FIFOFLGS & 0x02 ) && !is_external_fifo_full() )
        goto REPEAT_WRITE;
      }
    }
  }

  // Handle IN EP6 host request
  if ( GPIFTRIG & 0x80 )  // if GPIF interface IDLE
  {
    if ( !is_external_fifo_empty() )  // if external FIFO is not empty
    {
      if ( !( EP68FIFOFLGS & 0x01 ) ) // if EP6 FIFO is not full
      {      
        Setup_FLOWSTATE_Read(); // setup FLOWSTATE registers for FIFO Read operation    
        SYNCDELAY;

REPEAT_READ:
    SYNCDELAY;
        GPIFTCB1 = 0x01;  // setup transaction count (512 bytes/2 for word wide -> 0x0100)
        SYNCDELAY;
        GPIFTCB0 = 0x00;
        SYNCDELAY;

        //*transaction_count_in += 1;
        GPIFTRIG = GPIFTRIGRD | GPIF_EP6; // launch GPIF FIFO READ Transaction to EP6 FIFO
        SYNCDELAY;

        while( !( GPIFTRIG & 0x80 ) ) // poll GPIFTRIG.7 GPIF Done bit
        {
        ;
        }

    if ( !is_external_fifo_empty() && !( EP68FIFOFLGS & 0x01 ) )
        goto REPEAT_READ;
      }
    }
  }
}
-Al-
Насчет скорости данного контроллера... У меня при шине 16 бит и частоте 48 МГц получилось прокачивать ~24МБ/сек (12МБ туда и 12МБ обратно), причем запись в буферы FIFO велась единичными словами, а не пакетами, при пакетной записи скорость естественно возрастет. Дескрипторы - по умолчанию. Драйвера стандартные (CyAPI), размер блока передачи 512кБайт.

PS тут забыл сказать, что передача идет через Bulk Endpoints
XShocK
Все больше и больше мне становиться интересно какой-же все-таки метод передачи является самым быстрым. И как лучше всего передавать данные по самому USB. Выиграю я в скорости если буду использовать Isochronous endpoints?
-=Vitaly=-
Цитата(XShocK @ Jan 10 2007, 07:32) *
Все больше и больше мне становиться интересно какой-же все-таки метод передачи является самым быстрым. И как лучше всего передавать данные по самому USB. Выиграю я в скорости если буду использовать Isochronous endpoints?



Аналогично, интересуюсь тем же вопросом!. Тут еще упоминался метод отдельных тредов. Если можно в 2х словах о нем.

СПС!
-Al-
Цитата(-=Vitaly=- @ Jan 10 2007, 10:00) *
Цитата(XShocK @ Jan 10 2007, 07:32) *

Все больше и больше мне становиться интересно какой-же все-таки метод передачи является самым быстрым. И как лучше всего передавать данные по самому USB. Выиграю я в скорости если буду использовать Isochronous endpoints?



Аналогично, интересуюсь тем же вопросом!. Тут еще упоминался метод отдельных тредов. Если можно в 2х словах о нем.

СПС!

С изохронным режимом передачи кроме геморроя ничего больше не обретете, приличную скорость можно выжать и из Bulk. Метод отдельных тредов состоит лишь в том, что прием/передача осуществляется в отдельном потоке по отношению к основной программе, посмотрите пример CyAPI/Examples/Streamer в USB DevStudio.
Gate
3 доки с сайта сайпресс о измерении скорости и о результатах этих измерений.
jur
Цитата(-=Vitaly=- @ Jan 10 2007, 09:00) *
Цитата(XShocK @ Jan 10 2007, 07:32) *

Все больше и больше мне становиться интересно какой-же все-таки метод передачи является самым быстрым. И как лучше всего передавать данные по самому USB. Выиграю я в скорости если буду использовать Isochronous endpoints?
Аналогично, интересуюсь тем же вопросом!
Так нет ничего проще, как взять и посчитать :-) Возьмем тактовую частоту USB 480 MHz и поделим ее на 8 бит. Получается 60 МБайт/сек. Это теоретический предел. Далее заглядываем в "Universal Serial Bus Specification Revision 2.0" стр. 46 и 55 и видим, что теоретический предел и там указан в 60 МБайт/сек. Из этого числа нужно вычесть накладные расходы на протокол (они небольшие) и трудноучитываемые расходы на остальное (хаб, корневой драйвер, драйвер устройства, операционную систему и т.п.). Инженерная прикидка позволяет надеяться в среднем на потолок в 30-40 МБайт/сек. Однако, достичь максимальной скорости, IMHO, не так легко...

Что касается Isochronous endpoints, то, как верно отметил коллега -Al-, кроме геморроя других выигрышей не наблюдается. Потом, не забывайте, Isochronous endpoints не обеспечивают безошибочную передачу данных. Исказился блок при передаче - хрен с ним, играем дальше! В спокойных условиях передачи это, наверное, крайне редкий случай, но условия всякими могут быть...

Цитата(-=Vitaly=- @ Jan 10 2007, 09:00) *
Тут еще упоминался метод отдельных тредов. Если можно в 2х словах о нем.
Ну, это очень просто. Как написать программу для Винды, чтобы она быстро реагировала на приём данных? Ведь виндовая программа просто ждет событий в основном цикле сообщений. Механизм сообщений Винды - штука достаточно небыстрая. Если работать через него, то ничего не успеть. Поэтому вполне логично выделить кусок кода, работающий с быстрым каналом USB, в отдельный поток. В этом случае получается что-то похожее на ОСРВ: поток "засыпает" до получения очередной порции данных из USB, а когда эти данные приходят, то поток получает управление намного скорее, чем обычным образом посредством механизма сообщений. Такая технология позволяет максимально быстро принимать/передавать данные, т.к. системные накладные расходы минимизируются. Кроме того, программировать отдельный тред намного проще :-) Не нужно заморачиваться другими вопросами, можно целиком сосредоточиться на задаче быстрой передачи данных.

Цитата(Gate @ Jan 10 2007, 10:59) *
3 доки с сайта сайпресс о измерении скорости и о результатах этих измерений.
Спасибо за интересную информацию! В этих примерах достигается примерная скорость в ~20-24 МБайт/сек. Похоже, что на это примерное значение и следует ориентироваться в своих инженерных прикидках. Т.е. это, по видимому, те значения, которые могут быть сравнительно несложно повторены, достигнуты обычным путем, без очень сложных подходов к решению задачи.
XShocK
Цитата(jur @ Jan 11 2007, 10:24) *
Спасибо за интересную информацию! В этих примерах достигается примерная скорость в ~20-24 МБайт/сек. Похоже, что на это примерное значение и следует ориентироваться в своих инженерных прикидках. Т.е. это, по видимому, те значения, которые могут быть сравнительно несложно повторены, достигнуты обычным путем, без очень сложных подходов к решению задачи.


В том и дело, что у меня как раз и получается 20 мб/сек в лучшем случае. Это при том, что чипсет как раз ICH5. Если не затруднит, помогите ускорить мое творение. Выкладываю все исходники включая GPIF проект(используются FIFOrd и FIFOwr, одиночные давно не использовал). Я не могу понять, что у меня неправильно написано.

http://rinat.acm.jhu.edu/all_source.zip

Спасибо.
jur
Цитата(XShocK @ Jan 13 2007, 01:42) *
В том и дело, что у меня как раз и получается 20 мб/сек в лучшем случае. Это при том, что чипсет как раз ICH5. Если не затруднит, помогите ускорить мое творение. Выкладываю все исходники включая GPIF проект (используются FIFOrd и FIFOwr, одиночные давно не использовал). Я не могу понять, что у меня неправильно написано.
Хм... На первый взгляд, вроде, все верно. Только я обратил бы внимание на функцию

DWORD WINAPI thread_usb_loop (void *data)

Мне представляется, что в ней блок вызовов

usb_begin_out_transfer(s_tex_orig, TEXTURE_WIDTH * TEXTURE_HEIGHT);
usb_begin_in_transfer(s_tex_processed, TEXTURE_WIDTH * TEXTURE_HEIGHT);
usb_wait_out_transfer_finish();
usb_wait_in_transfer_finish();


не совсем рационально использует CPU. Например, после выполнения операции OUT получается непроизводительная трата времени на ожидание операции IN. Наверное, стоило бы взглянуть на пример Streamer из Cypress'овской USB DevStudio. В этом примере рассматривается очень рациональный метод потокового выполнения заданий. Т.е. запускается сразу несколько операций считывания (в этом примере производится считывание данных в компьютер). В твоем примере, видимо, стоит сделать точно так же, но усложнить алгоритм, добавив в него еще и вывод кадров. Может быть, стоило бы сделать отдельные треды для вывода кадров и для их последующего ввода. Тогда степень распараллеливания может быть максимальной. Глубина очереди, IMHO, может быть на уровне примерно 4-х операций (т.е. число элементов в очереди операций). Также следует помнить о синхронизации вывода кадров и их последующего ввода в компьютер. Думаю, что тут можно применить что-то простенькое, типа счетчика, изменяемого в закрытой секции каждым потоком (тредом).

Ну и, наконец, думаю, что стоило бы поиграться величиной порций видео-данных, передаваемых туда и обратно. Может быть можно получить выигрыш в скорости за счет более плавной загрузки канала передачи, если передавать не весь кадр целиком, а разбить его на кусочки по 8-16-32 КБайт. Объяснить не могу, но закрадывается чувство, что работа драйвера с большими порциями данных на одну операцию может вызвать дополнительные накладные расходы. Впрочем, в этом вопросе я не силен, возможно этот мой взгляд ошибочен.

Кроме того, думаю, стоило бы прикинуть время выполнения операций, т.е. в треде вывода считать период выдачи кадров, а в треде ввода, соответственно, их считывания. Для чистоты эксперимента и получения наиболее точных значений производительности, стоило бы временно выключить операции OpenGL, чтобы получить чистые цифры самой передачи по USB. Для подсчета времени следует использовать максимально точный в Винде таймер QueryPerformanceCounter. Например я делаю так: накапливаю в сумматоре показания QueryPerformanceCounter и запоминаю число полученных пакетов, а затем раз в секунду (в основной виндовой программе) делю одно на другое, перевожу в секунды и вывожу на индикацию. Причем, тут следовало бы накапливать целый ряд сумматоров: период вывода, время очередного вывода, период ввода, время очередного ввода, и, может быть, еще какие-нибудь ключевые моменты алгоритма передачи данных.
Warlord
Мне удалось достичь скорости 33МБайт\с на Bulk In на драйвере ezusb.sys, думаю можно поднять еще немного, переписав функцию драйвера приемопередачи. И поднять еще немного, увеличив скорость заполнения фифо (щас у меня примерно 36Мгц) до штатных 48Мгц. У меня другая проблема, хочу сказать драйверу (один раз), получи-ка асинхронно эти 33МБ вот в этот буфер, а когда получишь, дерни рабочий поток, чтоб обработал. Так вот беда в том, что пока драйвер будет получать эти 33МБ (примерно сек) ОС замрет на это время, а это не есть гуд...
jur
Цитата(Warlord @ Jan 15 2007, 16:18) *
Мне удалось достичь скорости 33МБайт\с на Bulk In на драйвере ezusb.sys, думаю можно поднять еще немного, переписав функцию драйвера приемопередачи.
Здорово! А ты взял стандартный драйвер ezusb.sys, или "доработал его напильником"? Интересно, как он в сравнении с CyUsb.sys? А что нужно переписать в функции приемопередачи драйвера? (Я с драйверами еще не ковырялся, они мне представляются этакими страшными, таинственными и очень сложными монстрами :-) )

Цитата(Warlord @ Jan 15 2007, 16:18) *
У меня другая проблема, хочу сказать драйверу (один раз), получи-ка асинхронно эти 33МБ вот в этот буфер, а когда получишь, дерни рабочий поток, чтоб обработал. Так вот беда в том, что пока драйвер будет получать эти 33МБ (примерно сек) ОС замрет на это время, а это не есть гуд...
Да... Похоже, что следует, все-таки, разбивать большой объем передачи на относительно небольшие кусочки. Тогда и ОС не будет притормаживать, и другие задачи смогут выполняться более-менее нормально (хотя полностью "прозрачно", конечно, не будет, больно уж скорость передачи здоровая, это неизбежно должно немного чувствоваться).
Warlord
2jur
Я взял стандарнтый ezusb.sys. Про CyUsb.sys не знаю, не пробовал, но думаю что выигрыша уже не будет. Так как исходников его нету, а я его ставил как-то раз, то могу предположить, что код, ответственный за приемопередачу, врядли короче и чище чем у ezusb.sys. Поверхностно они отличаются способом создания устройства. ezusb.sys создает устройство "EZUSB-0" а CyUsb.sys действует через GUID.
Много доработать не получится, так как там все просто и "лишних" вызовов на чем можно съэкономить почти нет. Доработка заключается в увеличении входного буфера, в оригинале драйвер принимает не больше 2^16 байт за раз, но у меня максимальная скорость была при 2^15. Так вот, чтобы получить 33Мега надо 1024 раза вызвать драйвер с буфером 2^15. А это "лишние" накладные расходы. Да и прога будет заниматься только тем что вызывать драйвер и ждать пока придет очередная порция, а обрабатывать будет некогда. Вот тогда и родился вариант отдать драйверу весь буфер 33МБ, и когда он заполнится, взведется событие, по которому аппилуха обработает данные.
jur
Цитата(Warlord @ Jan 16 2007, 09:00) *
Доработка заключается в увеличении входного буфера, в оригинале драйвер принимает не больше 2^16 байт за раз, но у меня максимальная скорость была при 2^15.
Большое спасибо за разъяснение!

Цитата(Warlord @ Jan 16 2007, 09:00) *
Так вот, чтобы получить 33Мега надо 1024 раза вызвать драйвер с буфером 2^15. А это "лишние" накладные расходы. Да и прога будет заниматься только тем что вызывать драйвер и ждать пока придет очередная порция, а обрабатывать будет некогда. Вот тогда и родился вариант отдать драйверу весь буфер 33МБ, и когда он заполнится, взведется событие, по которому аппилуха обработает данные.
Хм... Снова на ум приходит все тот же пример Streamer из Cypress'овской USB DevStudio. Взгляни, там очередь заданий запускается вот таким образом:

// Queue-up the first batch of transfer requests
for (i=0; i< QueueSize; i++) contexts[i] = dlg->InEndPt->BeginDataXfer(buffers[i], len, &inOvLap[i]);


Из этого примера видно, что происходит выполнение следующего приема данных параллельно с их обработкой в прикладной программе, т.е. получили данные из первого запроса (и снова перезапустили, чтобы очередь была постоянно заполненна) и можем их обрабатывать, а драйвер тем временем качает дальше. Я пробовал поиграться параметрами такого запуска на слабенькой embedded-материнке (VIA EPIA SP, PIII 1.3 GHz, 17 x 17 cm) и получил хорошие показатели сбалансированности нагрузки при 4-х запросах в очереди и 8 блоках в каждом запросе (т.е. порция данных 4 КБ). Может быть и в твоем случае можно применить похожий механизм? Тогда не нужно будет организовывать такой большой буфер в драйвере. Ведь в этом случае получится хорошее распараллеливание процесса: драйвер порции данных качает, а приложение их обрабатывает по мере поступления. Хотя я на таких больших скоростях не работал, возможно мои рассуждения ошибочны.
Warlord
Да, щас сам глянул CyUSB.sys и увидел, что этот драйверок намного навороченнее чем ezusb.sys. Там и потоки запускаются, и события сбрасываются\устанавливаются и еще много чего интересного делается. А потом я глянул Streamer и похоже что так оно и есть, порциями работа, щас гляну поподробнее как это функционирует. Очень даже может быть это и есть, то чего исчу smile.gif
nicom
Цитата(Warlord @ Jan 15 2007, 17:18) *
Мне удалось достичь скорости 33МБайт\с ...думаю можно поднять еще немного, переписав функцию драйвера приемопередачи.... И поднять еще немного, увеличив скорость заполнения фифо ...


...прошу прощения, что встрял в обсуждение...

А на какую максимальную скорость можно расчитывать для случая непрерывного потока данных в одну сторону (из устройства в компьютер)?
т.е. достиг ли кто нибудь скорости в 40МБайт в сек в случае передачи данных в течении, например, 1часа (144Гбайта) абсолютно без потерь данных?...
это про ХХ68013..., хотя, и не обязятельно...
jur
Цитата(nicom @ Jan 16 2007, 11:45) *
А на какую максимальную скорость можно расчитывать для случая непрерывного потока данных в одну сторону (из устройства в компьютер)?
IMHO, очень много от чего зависит. От железа, драйверов, прикладной программы, операционки, наконец. Судя по опыту коллеги Warlord, похоже, что скорость в 40 МБайт/сек достижима (хотя это и нелегко).

Цитата(nicom @ Jan 16 2007, 11:45) *
т.е. достиг ли кто нибудь скорости в 40МБайт в сек в случае передачи данных в течении, например, 1часа (144Гбайта) абсолютно без потерь данных?...
Без потерь данных - лёгко :-) Bulk endpoint обеспечивает безошибочную передачу. (Правда, в условиях сильных помех, при наличии ошибок передачи, упадет скорость, т.к. "булки" обеспечивают гарантированную доставку данных, но при этом идут перезапросы, т.е. не гарантируется траффик.)

Интересно, также, как работают Interrupt endpoints? Они ведь тоже гарантируют доставку, но еще и позволяют задавать время опроса. Т.е. и без ошибок и быстро. (?)

2 All. Просветите, пожалуйста, кто знает, чем хороши/плохи Interrupt endpoints? Может быть эти каналы позволяют сочетать скорость и надежность? (Согласно спецификации USB 2.0 скорость Interrupt endpoints такая же, как и Bulk endpoints, хотя это и напоминает бесплатный сыр...)

А количество данных... Если данные не нужно запоминать (вроде видеостриминга какого-нибудь), то передавай хоть терабайты :-) И ни один байт никуда не денется, если по Bulk или Interrupt...
nicom
Цитата
... похоже, что скорость в 40 МБайт/сек достижима (хотя это и нелегко).


Теоретически... - это понятно...
Вопрос в практической реализации...

2 ALL... похвастайтесь...
Warlord
Вчера примерялся к драйверку CyUSB.sys а сегодня утром получил свежие данные касательно скорости. Драйверок-то действительно побыстрее ezusb.sys будет smile.gif Мне удалось принять от железки 37МБ за 1000мс, т.е. за секунду. Это на 4МБ больше нежели с ezusb.sys. Причем прием асинхронный, что особенно радостно, огромное спасибо jur за инфу о Streamer. Об Interrupt Endpoints знаю немного, знаю что используются если устройство принадлежит к HID-классу, тогда родной драйверок виндофс САМ будет опрашивать и забирать данные с Endpoint-а, а аппликухе остается только забрать их у драйвера. Смущает только одно: параметр bInterval если он =1 то опрос проводится драйвером каждую 1мс даже при HI-speed. А это не есть гуд, поскольку очень редко, если размер Endpoint 1024 то терия дает всего 1МБ.. Возможно я заблуждаюсь и буду рад, если знающий поправит smile.gif
jur
Цитата(Warlord @ Jan 17 2007, 09:53) *
Вчера примерялся к драйверку CyUSB.sys а сегодня утром получил свежие данные касательно скорости. Драйверок-то действительно побыстрее ezusb.sys будет smile.gif
Мне он тоже как-то сразу понравился :-) Правда, повлияло еще и то, что в ходе общения со службой техподдержки Cypress'а они мне объяснили, что ezusb.sys хорош для обучения и как основа для разработки своего драйвера. А CyUsb.sys - это коммерческое изделие, годящееся для серийной продукции. Т.к. у меня нет опыта разработки драйверов под Винду, а драйвер CyUsb.sys авторы разрешают использовать совершенно бесплатно, то я на него и "запал". А уж когда я убедился, что по сравнению с драйверами от FTDI этот драйвер отличается еще и превосходной стабильностью, то мой выбор сузился до единственного варианта :-)

Цитата(Warlord @ Jan 17 2007, 09:53) *
... огромное спасибо jur за инфу о Streamer.
Всегда пожалуйста! Мы ведь тут именно для этого и обитаем, для общения и взаимопомощи :-)

Цитата(Warlord @ Jan 17 2007, 09:53) *
Смущает только одно: параметр bInterval если он =1 то опрос проводится драйвером каждую 1мс даже при HI-speed. А это не есть гуд, поскольку очень редко, если размер Endpoint 1024 то терия дает всего 1МБ.
Нет, это не так. Вот что сказано в разделе "5.7.4 Interrupt Transfer Bus Access Constraints" спецификации шины USB 2.0 (стр. 51):

High-speed endpoints can specify a desired period (2^bInterval-1)x125 µs, where bInterval is in the range 1 to (including) 16. The USB System Software will use this information during configuration to determine a period that can be sustained. The period provided by the system may be shorter than that desired by the device up to the shortest period defined by the USB (125 µs microframe or 1 ms frame).

Кроме того, в таблице 5-8 (на той же стр. 51) указаны цифры максимальных скоростей, которые такие же, как и для "булки".

Я так понял, что для High-speed ендпойнты период опроса может быть вплоть до 125 мксек. Кроме того, за один микрофрейм можно передавать еще и несколько пакетов (до трех штук вроде). В общем, интересная вещь, эти interrupt endpoints. Жаль, что пока очень непонятная...

P.S. У меня появилась одна мысль. Может быть ты можешь провести опыт? Попробуй, пожалуйста, сменить конфигурацию своей endpoint'ы с Bulk на Interrupt (с bInterval = 1) и запустить высокоскоростную передачу. Очень интересно было бы сравнить эти два канала. Какова максимальная скорость передачи? Насколько сильно при этом нагружается процессор? Чем вообще похожи/отличаются эти два вида ендпойнтов?
Warlord
Провел я опыт, результаты - 37МБ за 9.4сек, т.е. почти в 10 раз медлененнее. Загрузка проца 10-8-7-5-4-10-0 (P4-2800). Все параметры перепроверил EP bAttributes 0x03 bInterval=0x01, все как надо, девайс говорит - HiSpeed, использую CCyInterruptEndPoint, все как доктор прописал, но увы, что-то не срастается...
jur
Цитата(Warlord @ Jan 18 2007, 09:15) *
Провел я опыт, результаты - 37МБ за 9.4сек, т.е. почти в 10 раз медлененнее. Загрузка проца 10-8-7-5-4-10-0 (P4-2800).
Большое тебе спасибо за информацию! Очень интересно! Теперь видно, что Bulk и Interrupt ендпойнты чем-то отличаются. Причем, судя по результатам твоего опыта, отличаются существенно. Однако, при чтении спецификации на USB 2.0 это различие как-то не бросается в глаза... Черт... Придется углубиться в вопрос...
Warlord
Тут главное понять для чего вообще нужен это тип EP, немного странно, что у Cypress нет ни одного примера с использованием такого EP. Единственное применение, которое я нашел и реализовал - это HID устройство, виндовый драйвер которого HIDUsb.sys сам опрашивает железяку, а мне оставалось только забирать данные через ReadFile.
jur
Привет!

Провел некоторые эксперименты (P4, 3.06 GHz). Я сделал модификацию фирмваре FX2 так, чтобы она постоянно передавала блок данных (там просто мусор, сами данные неважны, передается просто 512 байт). А на компьютерной стороне я применил пример Streamer, который обращается к драйверу, получает данные и ничего с ними не делает, просто считает скорость передачи. Пробовал на двух одинаковых компьютерах. На первом установлена память DDR333. Скорость передачи была порядка 37.5 МБайт/сек. Точно такая же, какую получил в своих опытах коллега Warlord. А на втором установлена память DDR400. При этом скорость передачи возросла почти до 40 тысяч МБайт/сек. Вот скриншоты со второго компьютера:



Потом я еще увеличил число пакетов и длину очереди, скорость еще чуток возросла, но ненамного.

Однако, выплыл ньюанс, гробящий на корню мою быструю передачу. После примерно полутора минут передачи скорость падает больше чем на порядок и дальше болтается у этой очень небольшой величины. Что бы это могло значить? Вот поясняющие скриншоты:



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

Предварительный (еще очень ранний) вывод: скорость под 40 МБайт/сек простыми методами недостижима. Коллеги, очень прошу, поделитесь, не сталкивались ли вы с подобными эффектами? Особенно настораживает падение скорости передачи после полутора минут (!) после начала передачи.

Coming soon. Сейчас готовлюсь пойти по стопам коллеги Warlord в направлении Interrupt endpoints :-)
-Al-
Цитата(jur @ Jan 20 2007, 15:37) *
Потом я еще увеличил число пакетов и длину очереди, скорость еще чуток возросла, но ненамного.

Однако, выплыл ньюанс, гробящий на корню мою быструю передачу. После примерно полутора минут передачи скорость падает больше чем на порядок и дальше болтается у этой очень небольшой величины. Что бы это могло значить? Вот поясняющие скриншоты:
....
Особенно настораживает падение скорости передачи после полутора минут (!) после начала передачи.

Не обращайте на падение скорости внимания, это ошибка программы. Такое происходит потому, что расчет скорости ведется по формуле <суммарное переданное число байт>/<время передачи>. Просто суммарное переданное число байт быстро выходит за пределы unsigned long (32бита, 4ГБ), ну и соответсвенно, отсчет опять начинается с нуля, а время продолжает тикать как обычно smile.gif
jur
Цитата(-Al- @ Jan 20 2007, 15:05) *
Не обращайте на падение скорости внимания, это ошибка программы. Такое происходит потому, что расчет скорости ведется по формуле <суммарное переданное число байт>/<время передачи>. Просто суммарное переданное число байт быстро выходит за пределы unsigned long (32бита, 4ГБ), ну и соответсвенно, отсчет опять начинается с нуля, а время продолжает тикать как обычно smile.gif
Огромное спасибо, коллега, за разъяснение! Господи, сколько бессмысленных усилий пришлось бы потратить, чтобы понять этот момент! Я исправил переменную с ULONG на _int64 и все стало нормально: уже более 15 минут скорость держится стабильно на уровне 39957 КБайт/сек. Т.е. этот вопрос полностью снят.

Большое спасибо! :-)
jur
Привет!

"Играем дальше." (С) Жванецкий :-) Немножко исправил приложение Streamer, сделал передачу данных по Interrupt endpoint. Получил, как и положено, 8000 КБайт/сек. Так получилось потому, что я задал период опроса 1 микрофрейм, а величина ендпойнты составляет 1024 байт. Для контроля правильности эксперимента я параллельно запустил прежний Streamer с Bulk endpoint, который выжимает канал USB досуха. Как и следовало ожидать, эти 8000 КБайт были "откушены" от канала Bulk. Вот скриншоты (Interrupt и Bulk):



После этого я обратился к спецификации USB 2.0 (раздел 5.9 High-Speed, High Bandwidth Endpoints, стр. 56) и выставил число транзакций на микрофрейм равным 3-м. Однако, скорость передачи не изменилась! Вот скриншот:



Причем, число принимаемых байт верное (т.е. если задано 256 буферов по 3072 байта, то именно столько и принимается). Как это понимать? Что я делаю не так?

P.S. Настораживает то, что эти биты, которые задают число транзакций на микрофрейм, не маскируются приложениями. Т.е. USB View, к примеру, рапортует: wMaxPacketSize: 0x1400 (5120). Правда Streamer понимает правильно, но все равно как-то криво рапортует размер пакета в 3072 байта. Это ведь неверно! Размер пакета остался 1024 байт, это число пакетов на микрофрейм должно было бы быть три. А при задании 2-х пакетов на микрофрейм передача вообще не работает...
jur
Цитата(nicom @ Jan 16 2007, 20:32) *
2 ALL... похвастайтесь...
Попробую ;-)

Сегодня запустил свое приложение на дохлой embedded-материнке от VIA (плата EPIA SP). Удивился немерянно! На рабочем месте у меня компьютер Intel P4, 3066 MHz, плата MSI 865PE Neo3-V, чипсет i865PE, который дает 40000 КБайт/сек, а эта слабенькая платка качает со скоростью порядка 44000 КБайт/сек! Вот скриншот:



Однако!...
Warlord
Проделал те же шаги, что и jur, касательно bulk передачи, вот мой скриншот:

результаты - один в один smile.gif Блок питания не шумит, никаких подозрительных звуков не заметил smile.gif
Результат очень похож на практический потолок для Bulk.
Для просмотра полной версии этой страницы, пожалуйста, пройдите по ссылке.
Invision Power Board © 2001-2024 Invision Power Services, Inc.