|
spi_slave в Nios |
|
|
|
Dec 4 2013, 16:24
|

Лентяй
     
Группа: Свой
Сообщений: 2 203
Регистрация: 11-10-04
Из: Санкт-Петербург
Пользователь №: 843

|
Цитата(_Anatoliy @ Dec 4 2013, 17:34)  Подскажите,плз,как его нужно делать?Если с мастером более-менее понятно,то со слейвом у меня основная проблема - прерывания.Хочу написать свой обработчик,нужно чтобы по каждому принятому байту происходило прерывание основной программы.Как подключить обработчик?Нужен ли для этого VIC или можно обойтись без него?Литературу,конечно,читаю но как-то тяжело идёт процесс...С Nios раньше практически не работал.Может есть у кого похожий пример? Можно и без VIC, если не нужно быстрого отклика на прерывание. Используйте Internal контроллер (т.е. софтовый). Обработчик подключается специальной сишной функцией. Вот пример ниосовского кода с использованием пркрываний: Код #include "sys/alt_irq.h" #include "system.h"
#include "altera_avalon_pio_regs.h" #include "altera_avalon_timer_regs.h"
#include "pwm_avalon_interface_regs.h" #include "pwm_avalon_interface.h" #include "pwm_avalon_interface.c"
//********************** Global Variables *********************************************** volatile unsigned short int led_dir; volatile int return_code; volatile unsigned char i = 0; volatile unsigned int duty_cycle[8] = {499999, 150000, 60000, 10000, 5000, 2500, 800, 1};
//********************** ISR functions ************************************************** static void timer_isr (void * context) { volatile unsigned char* led_ptr; volatile unsigned char* dir_ptr;
IOWR_ALTERA_AVALON_TIMER_STATUS(TIMER_BASE, 0);
dir_ptr = (volatile unsigned char*)context; led_ptr = dir_ptr + 1;
return_code = altera_avalon_pwm_change_duty_cycle(LED_PWM_BASE, duty_cycle[i]); IOWR_ALTERA_AVALON_PIO_DATA(LED_PIO_BASE, *led_ptr);
if(*dir_ptr) { *led_ptr >>= 1; i--; } else { *led_ptr <<= 1; i++; } if(*led_ptr & 0x81) *dir_ptr ^= 0x1;
}
//********************** Auxiliary functions ******************************************** void check_return_code(unsigned int address, int return_code) { if(return_code != ALTERA_AVALON_PWM_OK) ; // print_error(address, return_code); }
//********************* Main function *************************************************** int main (void) { void* led_dir_ptr = (void*)&led_dir;
led_dir = 0x0100;
//Timer Initialization IOWR_ALTERA_AVALON_TIMER_CONTROL(TIMER_BASE, 0x0003); IOWR_ALTERA_AVALON_TIMER_STATUS(TIMER_BASE, 0);
IOWR_ALTERA_AVALON_TIMER_PERIODL(TIMER_BASE, 0x9f00); IOWR_ALTERA_AVALON_TIMER_PERIODH(TIMER_BASE, 0x0055);//0x0014);
//Register ISR for timer event alt_ic_isr_register(TIMER_IRQ_INTERRUPT_CONTROLLER_ID, TIMER_IRQ, timer_isr, led_dir_ptr, 0);
//Initialize PWM and Check Return Code return_code = altera_avalon_pwm_init(LED_PWM_BASE, 500000, 1); check_return_code(LED_PWM_BASE, return_code);
//Enable PWM and Check Return Code return_code = altera_avalon_pwm_enable(LED_PWM_BASE); check_return_code(LED_PWM_BASE, return_code);
//Start timer and begin the work IOWR_ALTERA_AVALON_TIMER_CONTROL(TIMER_BASE, 0x0007);
// IOWR_ALTERA_AVALON_PIO_DATA(LED_PIO_BASE, led);
while (1) check_return_code(LED_PWM_BASE, return_code);
}
--------------------
Чтобы слова не расходились с делом, нужно молчать и ничего не делать...
|
|
|
|
|
Dec 5 2013, 07:11
|

Утомлённый солнцем
     
Группа: Свой
Сообщений: 2 646
Регистрация: 15-07-06
Из: г.Донецк ДНР
Пользователь №: 18 832

|
Цитата(Stewart Little @ Dec 4 2013, 18:24)  Большое спасибо,буду пробовать. По ходу вопрос:какой смысл несёт передаваемый параметр context?Кто его формирует? Код static void timer_isr (void * context) А нет ли у Вас такого же примера для VIC?Или там всё аналогично,только функции другие?
|
|
|
|
|
Dec 5 2013, 08:58
|

Утомлённый солнцем
     
Группа: Свой
Сообщений: 2 646
Регистрация: 15-07-06
Из: г.Донецк ДНР
Пользователь №: 18 832

|
Цитата(alexPec @ Dec 5 2013, 10:31)  Сами ставим вроде. Можно поставить указатель на статическую переменную, структуру, внешний порт, или еще чего, чтобы в обработчике брать/писать данные в контекст. Да,спасибо,я уже понял что указатель задаётся здесь как led_dir_ptr. Код alt_ic_isr_register(TIMER_IRQ_INTERRUPT_CONTROLLER_ID, TIMER_IRQ, timer_isr, led_dir_ptr, 0);
|
|
|
|
|
Dec 5 2013, 15:58
|

Утомлённый солнцем
     
Группа: Свой
Сообщений: 2 646
Регистрация: 15-07-06
Из: г.Донецк ДНР
Пользователь №: 18 832

|
Цитата(Копейкин @ Dec 5 2013, 17:01)  М.б. компилятор не видит декларации прототипа функции? Нет,для этого случая у него есть варнинг: Код top.c:31: warning: implicit declaration of function 'Irq_init' Цитата(Konst_777 @ Dec 5 2013, 17:05)  Полезно поставить FIFO, хотя бы на несколько байт, чтобы обеспечить переход между клоковыми доменами и разгрузить процессор Nios II. Согласен,в общем случае полезно разгружать,но у меня здесь нет фоновых задач,только выполнение команд.Не для чего разгружать. Цитата(Stewart Little @ Dec 5 2013, 17:33)  VIC или не VIC - для софта без разницы. Все абсолютно аналогично. Спасибо. А как правильно в эклипсе подключать глобальные переменные?Пробовал объявлять в Main.c а в другие файлы подсовывал их как extern, идут ошибки multiple definition.Пробовал объявлять в одном файле global.h и включал его во все файлы - тоже самое.
|
|
|
|
|
Dec 6 2013, 05:22
|
Знающий
   
Группа: Свой
Сообщений: 555
Регистрация: 14-10-09
Пользователь №: 52 939

|
Цитата(_Anatoliy @ Dec 5 2013, 18:58)  А как правильно в эклипсе подключать глобальные переменные?Пробовал объявлять в Main.c а в другие файлы подсовывал их как extern, идут ошибки multiple definition.Пробовал объявлять в одном файле global.h и включал его во все файлы - тоже самое. Я делаю так: xxx.cКод unsigned char start=0; xxx.hКод extern unsigned char start; main.cКод #include "xxx.h" if(start) { }
|
|
|
|
|
Dec 6 2013, 08:59
|
Частый гость
 
Группа: Участник
Сообщений: 190
Регистрация: 7-11-07
Из: С-Петербург
Пользователь №: 32 134

|
В *.h обычно ставят "предохранители" от повторного подлючения: CODE #ifndef __HEADER_H__ #define __HEADER_H__ 1 . . . /* всякие декларации */ . #endif
|
|
|
|
|
Dec 6 2013, 09:07
|
Знающий
   
Группа: Свой
Сообщений: 549
Регистрация: 1-06-05
Пользователь №: 5 644

|
Цитата(_Anatoliy @ Dec 6 2013, 11:30)  Если делаю объявления переменных в теле файлов *.с то компилится без ошибок,как только выношу их в файлы *.h - сразу выскакивают ошибки multiple definition... А в xxx.h присутствуют волшебные строки ? Код #ifndef XXX_H_ #define XXX_H_ ... ... ... #endif /*XXX_H_*/ Эх, пока набирал, уже и спросили и ответили
|
|
|
|
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0
|
|
|