wmakc 0 Posted October 7, 2010 · Report post Контроллер должен периодически включаться по таймеру, выполнять работу, и уходить в какой-нибудь режим низкого потребления. Также должна быть возможность его пробуждения по Usart. Что нужно для этого сделать? Quote Ответить с цитированием Share this post Link to post Share on other sites
prst 0 Posted October 7, 2010 · Report post Контроллер должен периодически включаться по таймеру, выполнять работу, и уходить в какой-нибудь режим низкого потребления. Также должна быть возможность его пробуждения по Usart. Что нужно для этого сделать? по таймеру было бы не плохо проинициализировать на нужную тактовую, пыполнить задачу, и назад переинициализироваться с slow-clock и так со всеми перефириями, при этом читать еррату, что бы не оказались артефакты рядом с вашими перефириями Quote Ответить с цитированием Share this post Link to post Share on other sites
kovigor 0 Posted October 7, 2010 · Report post Контроллер должен периодически включаться по таймеру, выполнять работу, и уходить в какой-нибудь режим низкого потребления. Также должна быть возможность его пробуждения по Usart. Что нужно для этого сделать? У Атмела целый документ есть: http://www.atmel.com/dyn/resources/prod_do...nts/doc6217.pdf Вам нужен suspend mode (или Idle). Только не забудьте корректно подготовить SDRAM к переходу в этот режим ... Quote Ответить с цитированием Share this post Link to post Share on other sites
prst 0 Posted October 7, 2010 · Report post У Атмела целый документ есть: http://www.atmel.com/dyn/resources/prod_do...nts/doc6217.pdf Вам нужен suspend mode (или Idle). Только не забудьте корректно подготовить SDRAM к переходу в этот режим ... вообщето указанный Вами документ предназначен для AT91SAM9261 хотя и с него можно кое что черпнуть )) Quote Ответить с цитированием Share this post Link to post Share on other sites
kovigor 0 Posted October 7, 2010 · Report post вообщето указанный Вами документ предназначен для AT91SAM9261 хотя и с него можно кое что черпнуть )) Это не важно, там почти все совпадает. Я по этому документу делал Suspend для AT91SAM9XE512. Естественно, пришлось почитать даташит на этот МК ... Quote Ответить с цитированием Share this post Link to post Share on other sites
sasamy 0 Posted October 7, 2010 · Report post Что нужно для этого сделать? Поставить Linux ? suspend to ram там замечательно работает - одной строчки в шелле достаточно, или поучиться на исходниках Linux. Quote Ответить с цитированием Share this post Link to post Share on other sites
wmakc 0 Posted October 8, 2010 · Report post У Атмела целый документ есть: http://www.atmel.com/dyn/resources/prod_do...nts/doc6217.pdf Вам нужен suspend mode (или Idle). Только не забудьте корректно подготовить SDRAM к переходу в этот режим ... Можно поподробнее про подготовку SDRAM. Когда ее нужно перенастраивать, после перехода в Idle режим? Еще вопрос, посылаю контроллеру команду перехода в этот режим, а он просто зацикливается: AT91C_BASE_PMC->PMC_SCDR = AT91C_PMC_PCK; while ((AT91C_BASE_PMC->PMC_SCSR & AT91C_PMC_PCK) != AT91C_PMC_PCK); Кроме того в документе написано, что в этом режиме отключается только процессор "In Idle Mode, only the processor clock is stopped and the rest of the device is clocked by the master clock." Тоесть как я понимаю он должен продолжать реагировать на прерывания. И пре посылке данных по USART должен возвращаться в активный режим. Quote Ответить с цитированием Share this post Link to post Share on other sites
kovigor 0 Posted October 8, 2010 · Report post Можно поподробнее про подготовку SDRAM. Когда ее нужно перенастраивать, после перехода в Idle режим? Еще вопрос, посылаю контроллеру команду перехода в этот режим, а он просто зацикливается: AT91C_BASE_PMC->PMC_SCDR = AT91C_PMC_PCK; while ((AT91C_BASE_PMC->PMC_SCSR & AT91C_PMC_PCK) != AT91C_PMC_PCK); Кроме того в документе написано, что в этом режиме отключается только процессор "In Idle Mode, only the processor clock is stopped and the rest of the device is clocked by the master clock." Тоесть как я понимаю он должен продолжать реагировать на прерывания. И пре посылке данных по USART должен возвращаться в активный режим. 1. Я в своем Кейле в стартап-файле написал, чтобы память переходила в Self Refresh через 64 такта после последнего к ней обращения. Сначала я перестаю обращаться к ОЗУ, затем оно переходит в Self Refresh (осциллограф это подтверждает), а дальше я начинаю переводить МК в Suspend-режим. Я понимаю, что так делать, возможно, не очень красиво - необходимо посылать памяти команду перехода в Self Refresh самому, но как это сделать, я попросту не знаю. А описанное выше решение работает железно. 2. Вот извлечение из моего проекта - погружение процессора в Suspend, от начала и до конца: [pre] /*Low_Power_Mode();*/ //Peripheral Clock Disable AT91C_BASE_PMC->PMC_PCDR = 0x0000005c; //PIOA, PIOB, PIOC, USART clicking off //Going to "Slow clock mode": //MCKR: Program CSS field only //Master clock = Slow clock (according to Startup-file, Processor clock = Master clock / 2) AT91C_BASE_PMC->PMC_MCKR &= 0xfffffffc; //Wait until Main Master Clock is ready while(!(AT91C_BASE_PMC->PMC_SR & 0x00000008)){}; //Program all fields AT91C_BASE_PMC->PMC_MCKR = 0x00000200; //Processor clock = Slow clock, //Master clock = Processor clock / 4 //Wait until Main Master Clock is ready while(!(AT91C_BASE_PMC->PMC_SR & 0x00000008)){}; //PLLA off *AT91C_CKGR_PLLAR = 0x20000000; //////////////////////// AT91C_BASE_PMC->PMC_SCDR = 0x00000001; //Processor Clock off sbz = 0; __asm{MCR p15, 0, sbz, c7, c0, 4} //Проснулись ! Теперь надо все восстановить: Normal_Power_Mode(); [/pre] Да, именно так, будет возвращаться, но не сам собой. Вы должны будете после пробуждения процессора вручную все повключать, восстановить частоты и вернуть все "на круги своя": [pre] void Normal_Power_Mode(void) { //Peripheral Clock Enable AT91C_BASE_PMC->PMC_PCER = 0x0000005c; //PIOA, PIOB, PIOC, USART clocking on //Setup the PLL A *AT91C_CKGR_PLLAR = 0x20B3BF0C; //Wait until PLL A is stabilized while(!(AT91C_BASE_PMC->PMC_SR & 0x00000002)){}; //Program PRES field only AT91C_BASE_PMC->PMC_MCKR &= 0xffffffe3; //Processor clock = Slow clock //Wait until Main Master Clock is ready while(!(AT91C_BASE_PMC->PMC_SR & 0x00000008)){}; //Program all fields AT91C_BASE_PMC->PMC_MCKR = 0x00000102; //Processor clock = PLLA, //Master clock = Processor clock / 2 //Wait until Main Master Clock is ready while(!(AT91C_BASE_PMC->PMC_SR & 0x00000008)){}; } [/pre] Кстати, не забудьте перенастроить UART "перед сном", если будете снижать частоту его тактирования ... Quote Ответить с цитированием Share this post Link to post Share on other sites
wmakc 0 Posted October 10, 2010 (edited) · Report post 1. Я в своем Кейле в стартап-файле написал, чтобы память переходила в Self Refresh через 64 такта после последнего к ней обращения. Сначала я перестаю обращаться к ОЗУ, затем оно переходит в Self Refresh (осциллограф это подтверждает), а дальше я начинаю переводить МК в Suspend-режим. Я понимаю, что так делать, возможно, не очень красиво - необходимо посылать памяти команду перехода в Self Refresh самому, но как это сделать, я попросту не знаю. А описанное выше решение работает железно. Можно поподробнее про то, как вы переводите память в Self Refresh. Никогда так не делал, поэтому не совсем понимаю как это сделать Edited October 10, 2010 by wmakc Quote Ответить с цитированием Share this post Link to post Share on other sites
kovigor 0 Posted October 11, 2010 · Report post Можно поподробнее про то, как вы переводите память в Self Refresh. Никогда так не делал, поэтому не совсем понимаю как это сделать Не я перевожу, она сама туда переходит после последнего обращения. Главное контроллер в МК правильно настроить. См. также описание регистра SDRAMC_LPR ... Low_Power.bmp Quote Ответить с цитированием Share this post Link to post Share on other sites
wmakc 0 Posted October 13, 2010 · Report post Немного разобрался, потребление удалось снизить. Только столкнулся с проблемой. Включаю прерывания по USART по заполнению буфера, выключаю ядро. Так оно сразу возвращается в обычный режим. Начал смотреть и заметил, что как только включаю прерывания по USART, так прерывание сразу срабатывает. Даже если нет никакой передачи данных на контроллер. Немогу понять с чем это связано Quote Ответить с цитированием Share this post Link to post Share on other sites
kovigor 0 Posted October 14, 2010 · Report post Немного разобрался, потребление удалось снизить. Только столкнулся с проблемой. Включаю прерывания по USART по заполнению буфера, выключаю ядро. Так оно сразу возвращается в обычный режим. Начал смотреть и заметил, что как только включаю прерывания по USART, так прерывание сразу срабатывает. Даже если нет никакой передачи данных на контроллер. Немогу понять с чем это связано Вот, из описания контроллера PDC: " When the programmed data is transferred, an end of transfer interrupt is generated by the peripheral itself. " Ваш случай ? Если да, попробуйте увеличить буфер, чтобы он не заполнялся так быстро. Если нет, то у вас, возможно, уже установлен какой-то флажок прерывания в тот момент, когда МК засыпает. Не все флажки сбрасываются сами, некоторые необходимо сбрасывать вручную. Quote Ответить с цитированием Share this post Link to post Share on other sites
wmakc 0 Posted March 23, 2011 · Report post не знаю, может и глупый вопрос, но можно ли usart настроить на slow clock, а при срабатывании прерывания перестроить на максимальную скорость? или не перестраивать, но как настроить прерывания? Quote Ответить с цитированием Share this post Link to post Share on other sites