OpenEdv-开源电子网

 找回密码
 立即注册
正点原子全套STM32/Linux/FPGA开发资料,上千讲STM32视频教程免费下载...
查看: 4223|回复: 6

stm32f1单片机模拟SPI接口

[复制链接]

19

主题

58

帖子

0

精华

初级会员

Rank: 2

积分
65
金钱
65
注册时间
2015-8-23
在线时间
20 小时
发表于 2016-7-3 12:05:02 | 显示全部楼层 |阅读模式
50金钱
事情是这样的。
我最近在准备模拟SPI接口,现在问题来了,我在系统9倍频的情况下:假如连续有3个读取的代码,第一条可以读取且,之后的都是读取的0XFF。但是如果用仿真器单步执行就都可以读取且正确。

后来我试了5倍频,通讯就OK了。我想知道,这到底是咋回事,如何解决呢,请知道的大神给个提示,或者调试的方向,谢谢。

最佳答案

查看完整内容[请看2#楼]

是不是周末,大家都在忙啊?
正点原子逻辑分析仪DL16劲爆上市
回复

使用道具 举报

19

主题

58

帖子

0

精华

初级会员

Rank: 2

积分
65
金钱
65
注册时间
2015-8-23
在线时间
20 小时
 楼主| 发表于 2016-7-3 12:05:03 | 显示全部楼层
是不是周末,大家都在忙啊?
回复

使用道具 举报

19

主题

58

帖子

0

精华

初级会员

Rank: 2

积分
65
金钱
65
注册时间
2015-8-23
在线时间
20 小时
 楼主| 发表于 2016-7-3 14:52:03 | 显示全部楼层
自己给自己顶一下。
回复

使用道具 举报

0

主题

60

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
295
金钱
295
注册时间
2016-6-17
在线时间
60 小时
发表于 2016-7-4 15:43:05 | 显示全部楼层
时钟太快了,超出你的SPI从设备的要求了,看看芯片的SPI时序要求
回复

使用道具 举报

19

主题

58

帖子

0

精华

初级会员

Rank: 2

积分
65
金钱
65
注册时间
2015-8-23
在线时间
20 小时
 楼主| 发表于 2016-7-4 16:34:33 | 显示全部楼层
zzx499 发表于 2016-7-4 15:43
时钟太快了,超出你的SPI从设备的要求了,看看芯片的SPI时序要求

void Tx_Onebyte(unsigned char TxData)
{
        unsigned char i,j,k;

        SCK_DOWN;

        NOP();
        NOP();

        i = 0x80;
        j = 8;

        for(;j>0;j--)
        {
                k=TxData&i;

                if(k > 0)
            {
                        SDI_UP;
                         
                      SCK_UP;
                      NOP();
                          NOP();
                      NOP();
                      SCK_DOWN;
                        NOP();
                          NOP();
                      NOP();
            }
            else
            {
                      SDI_DOWN;
                         
                      SCK_UP;
                      NOP();
                          NOP();
                      NOP();
                      SCK_DOWN;
                        NOP();
                          NOP();
                      NOP();
            }
            i=i>>1;
  }

  SCK_DOWN;

}

unsigned char Rx_Onebyte(void)
{
  unsigned char i,j;

  SCK_DOWN;
  NOP();
  NOP();

  i=0x00;j=8;
  for(;j>0;j--)
  {
     i=i<<1;
     SCK_UP;
     //NOP();
     //NOP();
     //NOP();
     SCK_DOWN;
     //NOP();
     //NOP();
     if(SDO==0){i=i|0x00;}
     else {i=i|0x01;}
     NOP();
         NOP();
         NOP();
         NOP();
         NOP();
  }

  NOP();
  SCK_DOWN;
  NOP();
  return i;
}

unsigned char Rx_Frame(unsigned char Num)    //接收数据存储在SPI_Rxdat[]内;
{
          unsigned char i,cs;

        i=0;
          cs=0;
          Tx_Onebyte(SPI_Txdat[0]);
          Tx_Onebyte(SPI_Txdat[1]);
          cs=cs+SPI_Txdat[0];
          cs=cs+SPI_Txdat[1];

        for(;Num>0;Num--)
          {
                   SPI_Rxdat=Rx_Onebyte();
                   cs=cs+SPI_Rxdat;
                   ++i;
          }   

          SPI_Rxdat=Rx_Onebyte();
          cs=cs+SPI_Rxdat;                        //校验和未取反CS加最后一个校验和字节=0xff(CS=CS+~CS);
          NOP();
          NOP();
          NOP();

          if(cs==0xff){return 1;}                    //校验和正确返回1
          else return 0;                             //校验和错误返回0
}


unsigned char Tx_Frame(unsigned char Num)
{
        unsigned char i,cs;
          i=0;
          cs=0;

          for(;Num>0;Num--)
          {
            Tx_Onebyte(SPI_Txdat);
            cs=cs+SPI_Txdat;
            i++;
          }
          cs=~cs;
          Tx_Onebyte(cs);
          NOP();
          NOP();
          NOP();
          NOP();
       
        return cs;
}



unsigned char RN8302_Rdat(unsigned int bank,unsigned char addr,unsigned char num)
{
        unsigned char Check=0;

          CS_DOWN;

          if(num<5)                         //最大同时读4个寄存器;
          {
                   SPI_Txdat[0]=addr;               //发送首地址;
                   SPI_Txdat[1]=0x00|(bank<<4);     //地址高三位;
                   Check=Rx_Frame(num);
                CS_UP;
          }
          else
          {
            Check=0;                        //否则错误;                        
          }

           return Check;                    //接受数据正确;返回1;            
}

unsigned char RN8302_Wdat(unsigned int bank,unsigned char addr,unsigned char num,...)
{
        unsigned int i=0;
           unsigned char temp=0;
           unsigned char Check=0;
           va_list argp;

           CS_DOWN;
           temp=num+2;

           if(num<4)
           {
            va_start(argp,num);
            SPI_Txdat[0]=addr;
            SPI_Txdat[1]=0x80|(bank<<4);

                for(;num>0;num--)
            {
                     SPI_Txdat[i+2]=va_arg(argp,unsigned char);
                     ++i;
            }

                va_end(argp);
            Check=Tx_Frame(temp);
                CS_UP;
   }
   else
   {
             Check=0;
   }

   return Check;
}
1.png
2.png
3.png
回复

使用道具 举报

0

主题

18

帖子

0

精华

新手上路

积分
41
金钱
41
注册时间
2016-6-28
在线时间
7 小时
发表于 2016-7-4 22:16:09 | 显示全部楼层
把GPIO的时钟降低一点试试呗
回复

使用道具 举报

19

主题

58

帖子

0

精华

初级会员

Rank: 2

积分
65
金钱
65
注册时间
2015-8-23
在线时间
20 小时
 楼主| 发表于 2016-7-5 13:18:06 | 显示全部楼层
Libra_jiang 发表于 2016-7-4 22:16
把GPIO的时钟降低一点试试呗

问题已经找到了。谢谢
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则



关闭

原子哥极力推荐上一条 /2 下一条

正点原子公众号

QQ|手机版|OpenEdv-开源电子网 ( 粤ICP备12000418号-1 )

GMT+8, 2025-6-11 08:43

Powered by OpenEdv-开源电子网

© 2001-2030 OpenEdv-开源电子网

快速回复 返回顶部 返回列表