Страница 1 из 1

STM32VLDISCOVERY SPI &%#^!!&!@

Добавлено: Сб авг 25, 2012 12:39:07
dinets
Грусть пичаль огорчение досада!

SPI (первый) рабаотает крайне странным образом
точнее он сам работает как надо но флаги и вовсе какието не упровлеяемые
(может уже подымалось)
(сутки назад написал полностью програмную работу с переферией двумя сдвиговыми регистрами управляющие семисегментом использую только данные, сдвиговый клок , паралельный клок, как работать с ней знаю!)

SPI мне удалось запустить (чтоб хоть както, непонятоно для меня, работало) используя примеры отселе http://forum.easyelectronics.ru/viewtop ... 7&start=50

программа ведёт себя крайне странно, и результаты работы, сработка флагов, можт менятся в зависимости в дебаге ли МК или нет (без дебага работает)

а вот с прерываниями завал ничего не работает и не поянтно что где куда!

Код: Выделить всё

//=======================
// STM32VLDISCOVERY tutorial
// Lesson 5. Blinking with timer hardware
// Copyright : Radoslaw Kwiecien
// http://en.radzio.dxp.pl
// e-mail : radek(at)dxp.pl
//=======================
#include "stm32f10x.h"
#include <math.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>


//#include "antilib_gpio.h"
//=======================
// Defines
//=======================		'
//===============
// STM32 AntiLib Project
// Module : GPIO
// Description : Macros for configure GPIO's
// Author : Radoslaw Kwiecien
// e-mail : radek@dxp.pl
// website : http://en.radzio.dxp.pl
//===============

 

//===============
//
//===============	  
///////
#define LED_BLUE_GPIO GPIOC
#define LED_BLUE_PIN 8 

#define LED_GREEN_GPIO GPIOC
#define LED_GREEN_PIN 9 
//=======================
// main function
//=======================
   int i=0;
   void delay_ms(uint16_t value)
{
if (value==0) return;
  TIM2->ARR = value;                  //çàãðóçèòü çíà÷åíèå çàäåðæêè
  TIM2->CNT = 0;
  TIM2->CR1 = TIM_CR1_CEN;	      //çàïóñòèòü òàéìåð
  while((TIM2->SR & TIM_SR_UIF)==0){} //äîæäàòüñÿ êîíöà çàäåðæêè
  TIM2->SR &= ~TIM_SR_UIF;	      //ñáðîñèòü ôëàã
}

long bcd_pow[8];
 void  bcd_init()
 {	   int i;
  for( i=0;i<8;i++)	bcd_pow[i]=	pow(10,i);
 
 }

void to_bcd(char * s,int in)
{

 int j=0;
	int i=10;
 for( i=6;i>0;i--)
 {

 //int tmp= pow(10,i);
 int tmp= bcd_pow[i];
 s[j]=in/tmp ;
 in=in-tmp*s[j];
  j++;
 }
  s[j]=in ;
}

	char m[8]={0x3f,0x06,0x5b,0x4f,0x66,0x6d, 0x7d,0x00};
	//
	// 	char md[8]={1,0,0,0,0,0, 0,0};
				 char md[8]={0};
	//		char m[8];

				long incr=1;
		char incr_bcd[8]={0};
	 

void ledcode(char *s, int n)
{
 char led_code[10]= {0x3F,0x06,0x5B,0x4F,0x66,0x6D,0x7D,0x07,0x7F,0x6F};
int i=0;
char tmp;
  for (i=0; i<n;i++)
  {	tmp=led_code[s[i]];

  s[i]=tmp;
  
  }

}

void SPI1_IRQHandler(void)
{  uint16_t tmp=0;
GPIOA->ODR|= GPIO_ODR_ODR3;
  
 /*
  //ïðè÷èíà ïðåðûâàíèÿ - îêîí÷àíèå ïåðåäà÷è áàéòà
  if(SPI1->SR &= SPI_SR_TXE)
  {
     //âûïîëíÿåì êàêèå-òî äåéñòâèÿ      
  }
 
  //ïðè÷èíà ïðåðûâàíèÿ - ïðèíÿò áàéò äàííûõ
  if(SPI1->SR &= SPI_SR_RXNE)
  {
     tmp = SPI1->DR;                //ïðî÷èòàòü ïðèíÿòûå äàííûå
     //âûïîëíÿåì êàêèå-òî äåéñòâèÿ      
  }
 
  //ïðè÷èíà ïðåðûâàíèÿ - îøèáêà ðåæèìà âåäóùåãî
  if(SPI1->SR &= SPI_SR_MODF)
  {
    //ñáðàñûâàåì ôëàã ñîáûòèÿ, êîòîðîå âûçâàëî ïðåðûâàíèå è äåëàåì ÷òî-òî ïîëåçíîå
  }
 
  //ïðè÷èíà ïðåðûâàíèÿ - ïåðåïîëíåíèå ïðèåìíèêà äàííûõ
  if(SPI1->SR &= SPI_SR_OVR)
  {
    //ñáðàñûâàåì ôëàã ñîáûòèÿ, êîòîðîå âûçâàëî ïðåðûâàíèå è äåëàåì ÷òî-òî ïîëåçíîå
  }
 
  //ïðè÷èíà ïðåðûâàíèÿ - îøèáêà äàííûõ
  if(SPI1->SR &= SPI_SR_CRCERR)
  {
    //ñáðàñûâàåì ôëàã ñîáûòèÿ, êîòîðîå âûçâàëî ïðåðûâàíèå è äåëàåì ÷òî-òî ïîëåçíîå
  }
 	  */
} 


void SysTick_Handler (void) {
 
 
   incr++;
     to_bcd(incr_bcd,incr);
	 
 ledcode(incr_bcd,8);
  memcpy(m,incr_bcd,8);

 /* 

	 
 //  
  				   */

}
    int buf;
int main(void)
{SysTick_Config(SystemCoreClock / 10);
  bcd_init();  
  RCC->APB2ENR |= RCC_APB2ENR_IOPCEN; // Ïîäêëþ÷åíèå òàêòîâîãî ñèãíàëà
  RCC->APB2ENR |=  RCC_APB2ENR_AFIOEN;     //âêëþ÷èòü òàêòèðîâàíèå àëüòåðíàòèâíûõ ôóíêöèé        /
RCC->APB2ENR |=  RCC_APB2ENR_IOPAEN;     //âêëþ÷èòü òàêòèðîâàíèå ïîðòà À 
////////////

//PA3 âûõîä äâóõòàêòíûé, îáùåãî íàçíà÷åíèÿ,50MHz                             /
GPIOA->CRL   |=  GPIO_CRL_MODE3;    //
GPIOA->CRL   &= ~GPIO_CRL_CNF3;     //
GPIOA->BSRR   =  GPIO_BSRR_BS3;     //
  //âûâîä óïðàâëåíèÿ SS: âûõîä äâóõòàêòíûé, îáùåãî íàçíà÷åíèÿ,50MHz                             /
GPIOA->CRL   |=  GPIO_CRL_MODE4;    //
GPIOA->CRL   &= ~GPIO_CRL_CNF4;     //
GPIOA->BSRR   =  GPIO_BSRR_BS4;     //
 
//âûâîä SCK: âûõîä äâóõòàêòíûé, àëüòåðíàòèâíàÿ ôóíêöèÿ, 50MHz
GPIOA->CRL   |=  GPIO_CRL_MODE5;    //
GPIOA->CRL   &= ~GPIO_CRL_CNF5;     //
GPIOA->CRL   |=  GPIO_CRL_CNF5_1;   //
 
//âûâîä MISO: âõîä öèôðîâîé ñ ïîäòÿãèâàþùèì ðåçèñòîðîì, ïîäòÿæêà ê ïëþñó
GPIOA->CRL   &= ~GPIO_CRL_MODE6;    //
GPIOA->CRL   &= ~GPIO_CRL_CNF6;     //
GPIOA->CRL   |=  GPIO_CRL_CNF6_1;   //
GPIOA->BSRR   =  GPIO_BSRR_BS6;     //
 
//âûâîä MOSI: âûõîä äâóõòàêòíûé, àëüòåðíàòèâíàÿ ôóíêöèÿ, 50MHz
GPIOA->CRL   |=  GPIO_CRL_MODE7;    //
GPIOA->CRL   &= ~GPIO_CRL_CNF7;     //
GPIOA->CRL   |=  GPIO_CRL_CNF7_1;   // 
////////////////////////
 RCC->APB2ENR |= RCC_APB2ENR_SPI1EN; //ïîäàòü òàêòèðîâàíèå                                      /
SPI1->CR1     = 0x0000;             //î÷èñòèòü ïåðâûé óïðàâëÿþùèé ðåãèñòð
SPI1->CR2     = 0x0000;             //î÷èñòèòü âòîðîé óïðàâëÿþùèé ðåãèñòð
SPI1->CR1    |= SPI_CR1_MSTR;       //êîíòðîëëåð äîëæåí áûòü ìàñòåðîì    
//SPI1->CR1    |= SPI_CR1_BR;         //çàäàåì ñêîðîñòü
SPI1->CR1    |= SPI_CR1_SSI;        //îáåñïå÷èòü âûñîêèé óðîâåíü ïðîãðàììíîãî NSS
SPI1->CR1    |= SPI_CR1_SSM;        //ðàçðåøèòü ïðîãðàììíîå ôîðìèðîâàíèå NSS
//SPI1->CR1    |= SPI_CR1_SPE;        //ðàçðåøèòü ðàáîòó ìîäóëÿ SPI 
 SPI1->CR1    |= SPI_CR1_DFF;  // 16 bit 
 // SPI1->CR1    |= SPI_CR1_LSBFIRST ; // LSBFIRST – çàäàåò ñïîñîá ïåðåäà÷è (0 — ìëàäøèì ðàçðÿäîì âïåðåä, 1 -ñòàðøèì); 
  SPI1->CR1  |=SPI_CR1_CPHA;
    SPI1->CR1  |=SPI_CR1_CPOL; 
	SPI1->CR1    |= SPI_CR1_SPE;        //ðàçðåøèòü ðàáîòó ìîäóëÿ SPI 
 ////
   RCC->APB1ENR |= RCC_APB1ENR_TIM2EN;   //ïîäàòü òàêòèðîâàíèå íà TIM2
 TIM2->PSC     = 8000-1;               //íàñòðîèòü äåëèòåëü äëÿ ôîðìèðîâàíèÿ ìèëëèñåêóíä
 TIM2->CR1     = TIM_CR1_OPM;          //ðåæèì îäíîãî èìïóëüñà 
 ////////////////////
// SPI1->CR2 |= SPI_CR2_TXEIE;        //ðàçðåøèòü ïðåðûâàíèå ïî îêîí÷àíèþ ïåðåäà÷è               
 SPI1->CR2 |= SPI_CR2_RXNEIE;       //ðàçðåøèòü ïðåðûâàíèå, åñëè ïðèíÿò áàéò äàííûõ
//SPI1->CR2 |= SPI_CR2_ERRIE;        //ðàçðåøèòü ïðåðûâàíèå ïðè âîçíèêíîâåíèè îøèáêè 
/////////////////////////////
  // NVIC_EnableIRQ (SPI1_IRQn);      //âûçâàòü ôóíêöèþ, êîòîðàÿ ðàçðåøèò ïðåðûâàíèå îò ìîäóëÿ SPI1 

   while(1)
   {
   
   int s=0x40;
int j=0;	

	char mask=0x80;

for(j=0;j<7;j++){
   int i;
 	
  mask=0x80;
 
   GPIOA->ODR&=~ GPIO_ODR_ODR3;
 buf=m[i];
 buf=buf|(s<<8);
  while(!(SPI1->SR & SPI_SR_TXE));

  SPI1->DR = buf;  
    while (!(SPI1->SR & SPI_SR_RXNE)); 
	// int i;
	  for(i=0;i<1;i++){} 
  buf=SPI1->DR ;

			 

		  GPIOA->ODR|= GPIO_ODR_ODR3;
		  buf=0;
		  // delay_ms(1);
		//	SPI1->DR = buf; 
		//	 while (!(SPI1->SR & SPI_SR_TXE));
		
			 //	 GPIOA->ODR^= GPIO_ODR_ODR3;
		 // GPIOA->ODR^= GPIO_ODR_ODR3;
   s=s>>1;
}
   
   
   }
//to_bcd(incr_bcd,incr);

}
//=======================
// End of file
//=======================
   /*
    char s=1;
int j=0;	
char m[4]={0xFF,0xFF,0xFF,0xFF};
	char mask=0x80;

for(j=0;j<4;j++){
   int i;
 	
  mask=0x80;
for(i=0;i<8;i++)

{	
//GPIOC->ODR=GPIO_ODR_ODR2(a&mask);
if(	s&mask)	 GPIOC->ODR|=GPIO_ODR_ODR0; else  GPIOC->ODR&=~GPIO_ODR_ODR0;
mask=mask >>1;	
GPIOC->ODR^= GPIO_ODR_ODR2;
			GPIOC->ODR^= GPIO_ODR_ODR2;}
	
		 	 mask=0x80;
		for(i=0;i<8;i++)
{if(	m[j]&mask)	 GPIOC->ODR|=GPIO_ODR_ODR0; else  GPIOC->ODR&=~GPIO_ODR_ODR0;
mask=mask >>1;		
GPIOC->ODR^= GPIO_ODR_ODR2;

			GPIOC->ODR^= GPIO_ODR_ODR2;}


		 GPIOC->ODR^= GPIO_ODR_ODR1;
		  GPIOC->ODR^= GPIO_ODR_ODR1;
		     s=s<<1;
		  }
   */
//////////////////////////////////////////
//////////////////////////////////////////////
//////////////////////////////////////////////////
//////////////////////////////////////////////////
/*
RCC->APB2ENR |= RCC_APB2ENR_IOPCEN; // Ïîäêëþ÷åíèå òàêòîâîãî ñèãíàëà
 GPIOC->CRL |= GPIO_CRL_MODE0; // Íàñòðîéêà ðåæèìà PORTC.0 ñ ÷àñòîòîé 50 ÌÃö
    GPIOC->CRL &=~GPIO_CRL_CNF0; // Óñòàíîâêà ïðîñòîãî ðåæèìà öèôðîâîãî âûõîäà

   GPIOC->CRL |= GPIO_CRL_MODE1; // Íàñòðîéêà ðåæèìà PORTC.0 ñ ÷àñòîòîé 50 ÌÃö
    GPIOC->CRL &=~GPIO_CRL_CNF1; // Óñòàíîâêà ïðîñòîãî ðåæèìà öèôðîâîãî âûõîäà

    GPIOC->CRL |= GPIO_CRL_MODE2; // Íàñòðîéêà ðåæèìà PORTC.0 ñ ÷àñòîòîé 50 ÌÃö
    GPIOC->CRL &=~GPIO_CRL_CNF2; // Óñòàíîâêà ïðîñòîãî ðåæèìà öèôðîâîãî âûõîäà

   GPIOC->ODR|=GPIO_ODR_ODR0 ;

SysTick_Config(SystemCoreClock / 10);

  RCC->APB1ENR |= RCC_APB1ENR_TIM2EN;   //ïîäàòü òàêòèðîâàíèå íà TIM2
 TIM2->PSC     = 8000-1;               //íàñòðîèòü äåëèòåëü äëÿ ôîðìèðîâàíèÿ ìèëëèñåêóíä
 TIM2->CR1     = TIM_CR1_OPM;          //ðåæèì îäíîãî èìïóëüñà 

	//TIM3->CCR3 = i;  
//TIM3->CCR4=i;

while (1) {

 int s=0x40;
int j=0;	

	char mask=0x80;

for(j=0;j<7;j++){
   int i;
 	
  mask=0x80;
for(i=0;i<8;i++)

{	
//GPIOC->ODR=GPIO_ODR_ODR2(a&mask);
if(	s&mask)	 GPIOC->ODR|=GPIO_ODR_ODR0; else  GPIOC->ODR&=~GPIO_ODR_ODR0;
mask=mask >>1;	
GPIOC->ODR^= GPIO_ODR_ODR2;
			GPIOC->ODR^= GPIO_ODR_ODR2;}
	
		 	 mask=0x80;
		for(i=0;i<8;i++)
{if(	m[j]&mask)	 GPIOC->ODR|=GPIO_ODR_ODR0; else  GPIOC->ODR&=~GPIO_ODR_ODR0;
mask=mask >>1;		
GPIOC->ODR^= GPIO_ODR_ODR2;

			GPIOC->ODR^= GPIO_ODR_ODR2;}


		 GPIOC->ODR^= GPIO_ODR_ODR1;
		  GPIOC->ODR^= GPIO_ODR_ODR1;
		     s=s>>1;
			 delay_ms(3);
			 ///////////////////////////////
		
			 for(i=0;i<8;i++)
			 {
		 GPIOC->ODR&=~GPIO_ODR_ODR0;
			//  GPIOC->ODR|=GPIO_ODR_ODR0;
			 GPIOC->ODR^= GPIO_ODR_ODR2;
			 GPIOC->ODR^= GPIO_ODR_ODR2;
			 }
			 	 for(i=0;i<8;i++)
			 { //GPIOC->ODR|=GPIO_ODR_ODR0;
				GPIOC->ODR&=~GPIO_ODR_ODR0;
			 GPIOC->ODR^= GPIO_ODR_ODR2;
			 GPIOC->ODR^= GPIO_ODR_ODR2;}

			 	 GPIOC->ODR^= GPIO_ODR_ODR1;
		  GPIOC->ODR^= GPIO_ODR_ODR1;
		 

		//  delay_ms(1);
//	delay_ms(md[j]);
//	if (phase<15){	delay_ms(md[j]); 	}
		  }
  				
			//	if (phase<20){	 phase++;	} else {phase=1;};
}
*/

собственно кусок работы с SPI

Код: Выделить всё

 GPIOA->ODR&=~ GPIO_ODR_ODR3; // клок паралельный 0
 buf=m[i];
 buf=buf|(s<<8);
  while(!(SPI1->SR & SPI_SR_TXE));

  SPI1->DR = buf;  
    while (!(SPI1->SR & SPI_SR_RXNE)); 
	// int i;
	  for(i=0;i<1;i++){} 
  buf=SPI1->DR ;

			 

		  GPIOA->ODR|= GPIO_ODR_ODR3; //клок паралельный 1 выводим данные из сдвигового на выходной регистр


инит
RCC->APB2ENR |= RCC_APB2ENR_SPI1EN; //ïîäàòü òàêòèðîâàíèå /
SPI1->CR1 = 0x0000; //î÷èñòèòü ïåðâûé óïðàâëÿþùèé ðåãèñòð
SPI1->CR2 = 0x0000; //î÷èñòèòü âòîðîé óïðàâëÿþùèé ðåãèñòð
SPI1->CR1 |= SPI_CR1_MSTR; //êîíòðîëëåð äîëæåí áûòü ìàñòåðîì
//SPI1->CR1 |= SPI_CR1_BR; //çàäàåì ñêîðîñòü
SPI1->CR1 |= SPI_CR1_SSI; //îáåñïå÷èòü âûñîêèé óðîâåíü ïðîãðàììíîãî NSS
SPI1->CR1 |= SPI_CR1_SSM; //ðàçðåøèòü ïðîãðàììíîå ôîðìèðîâàíèå NSS
//SPI1->CR1 |= SPI_CR1_SPE; //ðàçðåøèòü ðàáîòó ìîäóëÿ SPI
SPI1->CR1 |= SPI_CR1_DFF; // 16 bit
// SPI1->CR1 |= SPI_CR1_LSBFIRST ; // LSBFIRST – çàäàåò ñïîñîá ïåðåäà÷è (0 — ìëàäøèì ðàçðÿäîì âïåðåä, 1 -ñòàðøèì);
SPI1->CR1 |=SPI_CR1_CPHA;
SPI1->CR1 |=SPI_CR1_CPOL;
SPI1->CR1 |= SPI_CR1_SPE; //ðàçðåøèòü ðàáîòó ìîäóëÿ SPI
////
RCC->APB1ENR |= RCC_APB1ENR_TIM2EN; //ïîäàòü òàêòèðîâàíèå íà TIM2
TIM2->PSC = 8000-1; //íàñòðîèòü äåëèòåëü äëÿ ôîðìèðîâàíèÿ ìèëëèñåêóíä
TIM2->CR1 = TIM_CR1_OPM; //ðåæèì îäíîãî èìïóëüñà
////////////////////
// SPI1->CR2 |= SPI_CR2_TXEIE; //ðàçðåøèòü ïðåðûâàíèå ïî îêîí÷àíèþ ïåðåäà÷è
SPI1->CR2 |= SPI_CR2_RXNEIE; //ðàçðåøèòü ïðåðûâàíèå, åñëè ïðèíÿò áàéò äàííûõ
//SPI1->CR2 |= SPI_CR2_ERRIE; //ðàçðåøèòü ïðåðûâàíèå ïðè âîçíèêíîâåíèè îøèáêè
/////////////////////////////
// NVIC_EnableIRQ (SPI1_IRQn); //âûçâàòü ôóíêöèþ, êîòîðàÿ ðàçðåøèò ïðåðûâàíèå îò ìîäóëÿ SPI1

Re: STM32VLDISCOVERY SPI &%#^!!&!@

Добавлено: Вс авг 26, 2012 22:36:00
dinets
ага начинает прояснятся
насамом деле статус опустошения буфера передачи SPI_SR_TXE появляется не после того как последний покинет контролёр а после того как как опустеет предварительный буфер который есть наш SPI1->DR

чтобы дождатся полного окончания передачи нужно подождать пока SPI_SR_TXE уйдёт в 1 а SPI1->SR & SPI_SR_BSY в ноль
этого всё хорошо но мне нужно подавать строб как раз после окончания передачи
в теле программы всё ок но если я захочу перекинуть всё это на прерывание как отловить этот момент?

Re: STM32VLDISCOVERY SPI &%#^!!&!@

Добавлено: Пн авг 27, 2012 20:41:40
dinets
победа
ловим прерывание SPI1->CR2 |= SPI_CR2_RXNEIE;

обработчик вышел такой

Код: Выделить всё

 int s=0x40;
  int j=0;
    
void SPI1_IRQHandler(void)
{ 
static	int i=0;
 uint16_t tmp=0;
	
   uint16_t buf=0;
  tmp=SPI1->DR ;
GPIOA->ODR&=~ GPIO_ODR_ODR3;
GPIOA->ODR|= GPIO_ODR_ODR3; 
	




  
 	 
  if(i==0) {
 
  // GPIOA->ODR&=~ GPIO_ODR_ODR3;

 buf=m[j];
 buf=buf|(s<<8);
  //while(!(SPI1->SR & SPI_SR_TXE));

  SPI1->DR = buf;  


  }
  else
  {
    SPI1->DR = 0; 
s=s>>1;
j++;
	 
  }
  //  while (!(SPI1->SR & SPI_SR_RXNE));
   // while((!(SPI1->SR & SPI_SR_TXE)));
//	while (SPI1->SR & SPI_SR_BSY);
//	 	  SPI1->DR = buf;  
//	   while(!(SPI1->SR & SPI_SR_TXE));
	// int i;
	//  for(i=0;i<1;i++){} 
//  buf=SPI1->DR ;


i++;

  if (j>=7) { j=0; 	 s=0x40;}
  if (i>1) {i=0;}
 

}
не забываем послать чтото в самом начале
для начала катавасии на прерываниях!
SPI1->DR=0;

Re: STM32VLDISCOVERY SPI &%#^!!&!@

Добавлено: Ср авг 29, 2012 12:14:04
coredumped
Маладэц! Сам спросил, обсуждал, нашел решение, поделился с народом :))

Re: STM32VLDISCOVERY SPI &%#^!!&!@

Добавлено: Чт авг 30, 2012 13:13:41
Satyr
Ох уж эта тяга к изобретением велосипеда с поводом и без повода :)))