|
|
  |
AT91SAM7S прерывание от UDP - SoF как убить? |
|
|
|
Oct 6 2006, 17:23
|

Профессионал
    
Группа: Свой
Сообщений: 1 202
Регистрация: 9-01-05
Из: Санкт-Петербург
Пользователь №: 1 861

|
UDP постоянно генерирует прерывание Start Of Frame. Перечитал всю доку. Из косяков нашел только то, что у меня AIC настраивался после UDP. Поменял. Результат тот же. Инициализация вот Код
[size="2"]void AT91F_HID_SetInt(void)
{
//Init interupt
AT91F_AIC_ConfigureIt (AT91C_BASE_AIC, AT91C_ID_UDP, UDP_INTERRUPT_LEVEL, AT91C_AIC_SRCTYPE_INT_HIGH_LEVEL, UDP_IRQ_Handler);
AT91F_UDP_DisableIt (AT91C_BASE_UDP, AT91C_UDP_SOFINT);
AT91F_UDP_InterruptClearRegister (AT91C_BASE_UDP, 0xFFFFFFFF);
AT91F_AIC_EnableIt (AT91C_BASE_AIC, AT91C_ID_UDP);
}
[/size] Все остальное работает.
--------------------
Если сверху смотреть, то сбоку кажется, что снизу ничего не видно.
|
|
|
|
|
Oct 7 2006, 09:25
|

Профессионал
    
Группа: Свой
Сообщений: 1 202
Регистрация: 9-01-05
Из: Санкт-Петербург
Пользователь №: 1 861

|
Цитата(nameless @ Oct 7 2006, 08:55)  У меня похожая проблема, только я жду прерываний по endbusres.... кстати, а где Вы разрешаете прерывание именно по SOF ??? не видно что-то... Я наоборот хочу его отключить.  Вроде разобрался. Косяк был, предположительно, в том, что в файле cstartup.s уже есть асемблерный код, который делавет все необходимые подготовки для обработки прерываний, а я еще и обработчик задал с директивой __irq А по endbusres у меня все нормально отлавливается. Вот, на всякий случай код инициализации: Код [size="2"] void AT91F_HID_SetInt(void)
{
//Init interupt
AT91F_AIC_ConfigureIt (AT91C_BASE_AIC, AT91C_ID_UDP, UDP_INTERRUPT_LEVEL, AT91C_AIC_SRCTYPE_INT_HIGH_LEVEL, UDP_IRQ_Handler);
AT91F_UDP_DisableIt (AT91C_BASE_UDP, AT91C_UDP_SOFINT);
AT91F_UDP_InterruptClearRegister (AT91C_BASE_UDP, 0xFFFFFFFF);
AT91F_AIC_EnableIt (AT91C_BASE_AIC, AT91C_ID_UDP);
}
[/size]
А вот обработчик:
Код [size="2"] //UDP interupt routine
void UDP_IRQ_Handler(void)
{
AT91PS_UDP pUDP = AT91C_BASE_UDP;
AT91_REG isr = pUDP->UDP_ISR;
AT91F_DBGU_Printk ("UDP_int\n\r");
//AT91F_DBGU_PrintHex(isr);
if (isr & AT91C_UDP_ENDBUSRES)
{
AT91F_UDP_InterruptClearRegister (AT91C_BASE_UDP, AT91C_UDP_ENDBUSRES);
// reset all endpoints
pUDP->UDP_RSTEP = (unsigned int) -1;
pUDP->UDP_RSTEP = 0;
// Enable the function
pUDP->UDP_FADDR = AT91C_UDP_FEN;
// Configure endpoint 0
pUDP->UDP_CSR[0] = (AT91C_UDP_EPEDS | AT91C_UDP_EPTYPE_CTRL);
// Enable Int endpoint 0
AT91F_UDP_EnableIt (AT91C_BASE_UDP, AT91C_UDP_EPINT0);
AT91F_DBGU_Printk(" -Bus reset\n\r");
}
if (isr & AT91C_UDP_RXSUSP)
{
AT91F_UDP_InterruptClearRegister (AT91C_BASE_UDP, AT91C_UDP_RXSUSP);
AT91F_DBGU_Printk(" -Suspend int\n\r");
}
if (isr & AT91C_UDP_RXRSM)
{
AT91F_UDP_InterruptClearRegister (AT91C_BASE_UDP, AT91C_UDP_RXRSM);
AT91F_DBGU_Printk(" -Resume int\n\r");
}
if (isr & AT91C_UDP_EXTRSM)
{
AT91F_UDP_InterruptClearRegister (AT91C_BASE_UDP, AT91C_UDP_EXTRSM);
AT91F_DBGU_Printk(" -External resume int\n\r");
}
if (isr & AT91C_UDP_SOFINT)
{
AT91F_UDP_InterruptClearRegister (AT91C_BASE_UDP, AT91C_UDP_SOFINT);
//AT91F_UDP_DisableIt (AT91C_BASE_UDP, AT91C_UDP_SOFINT);
AT91F_DBGU_Printk(" -Start of frame int\n\r");
}
if (isr & AT91C_UDP_WAKEUP)
{
AT91F_UDP_InterruptClearRegister (AT91C_BASE_UDP, AT91C_UDP_WAKEUP);
AT91F_DBGU_Printk(" -External resume int\n\r");
}
if (isr & AT91C_UDP_EPINT0)
{
AT91F_DBGU_Printk (" -EP0 Int!\n\r");
AT91F_HID_Enumerate(&HID);
AT91F_UDP_EpClear(AT91C_BASE_UDP, 0, AT91C_UDP_TXCOMP | AT91C_UDP_RX_DATA_BK0 | AT91C_UDP_RXSETUP | AT91C_UDP_ISOERROR | AT91C_UDP_RX_DATA_BK1);
AT91F_UDP_InterruptClearRegister (AT91C_BASE_UDP, AT91C_UDP_EPINT0);
}
if (isr & AT91C_UDP_EPINT1)
{
AT91F_DBGU_Printk (" -EP1 Int!\n\r");
AT91F_UDP_EpClear(AT91C_BASE_UDP, 1, AT91C_UDP_TXCOMP);
AT91F_UDP_InterruptClearRegister (AT91C_BASE_UDP, AT91C_UDP_EPINT1);
}
//if (HID.IsConfigured(&HID))
//AT91F_HID_Enumerate(&HID);
//AT91F_UDP_InterruptClearRegister (AT91C_BASE_UDP, AT91C_UDP_RXRSM);
//AT91F_AIC_ClearIt (AT91C_BASE_AIC, AT91C_ID_UDP);
//AT91F_AIC_AcknowledgeIt (AT91C_BASE_AIC);
}
[/size]
--------------------
Если сверху смотреть, то сбоку кажется, что снизу ничего не видно.
|
|
|
|
|
May 10 2007, 07:33
|
Участник

Группа: Новичок
Сообщений: 69
Регистрация: 12-10-05
Из: Калуга
Пользователь №: 9 539

|
Подскажите, пожалуйста, как решить следующую проблему с прерываниями UDP ENDBUSRES и RXRSM.
Пока устройство не подключено к компьютеру, постоянно идут прерывания ENDBUSRES и RXRSM (поочередно). Это нормально?
Это прерывание ENDBUSRES мешает мне передать дескриптор устройства на хост: подключаю устройство (на AT91RM9200) к компьютеру, включаю PullUp, возникает прер-ие ENDBUSRES, затем прер-ие EPOINT0 - получаю пакет SETUP (запрос дескриптора устройства), передаю первые 8 из 18 байт, снова прерывание по EPOINT0 - по флагу TX_COMP, передаю следующие 8 байт дескриптора, а вот здесь снова возникает прерывание по ENDBUSRES и я уже никогда не передаю последние 2 байта дескриптора устройства.
Из-за чего это случается? Когда должно происходить прер-ие ENDBUSRES? Только после подключения устройства к хосту и только 1 раз? И как отключить RXRSM?
AT91F_UDP_DisableIt(AT91C_BASE_UPD, AT91C_UPD_RXRSM) в обработчике прерывания по ENDBUSRES не помогает.
Спасибо.
|
|
|
|
|
  |
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0
|
|
|