打印
[STM32F4]

f4与f1/f4 硬件spi双机通信问题!

[复制链接]
2316|3
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
KC_CEC|  楼主 | 2014-4-11 16:15 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
本帖最后由 KC_CEC 于 2014-4-11 16:24 编辑

现有一个主机stm32f4,两个从机stm32f4和stm32f1。经过硬件spi进行全双工通信。

现在有两个问题:
1、我分别与两个从机相连接,通信比较正常。但是用示波器观察引脚,发现从机返回数据线(也就是MISO)会出现中间电平。中间电平在1.2V的样子!

2、但是为什么主机会正常稳定接收从机数据呢?
我猜因为GPIO内置TTL施密特触发器,所以能稳定忽视中间电平。但是如果主机CMOS的话那会不会导致数据错乱呢?

下面我贴上代码希望大家分析一下:
主机配置如下(stm32f4)
static void SPI_GPIO_Configuration(void)
{
        GPIO_InitTypeDef GPIO_InitStructure;

        RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOB ,ENABLE);
        GPIO_StructInit(&GPIO_InitStructure);

        GPIO_InitStructure.GPIO_Pin = GPIO_Pin_13 | GPIO_Pin_14 | GPIO_Pin_15;
        GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;
        GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;
        GPIO_InitStructure.GPIO_PuPd  = GPIO_PuPd_UP;
        GPIO_InitStructure.GPIO_Speed = GPIO_Speed_2MHz;
        GPIO_Init(GPIOB, &GPIO_InitStructure);

        GPIO_PinAFConfig(GPIOB, GPIO_PinSource13, GPIO_AF_SPI2);
        GPIO_PinAFConfig(GPIOB, GPIO_PinSource14, GPIO_AF_SPI2);
        GPIO_PinAFConfig(GPIOB, GPIO_PinSource15, GPIO_AF_SPI2);

        GPIO_InitStructure.GPIO_Pin = GPIO_Pin_12;
        GPIO_InitStructure.GPIO_Mode=GPIO_Mode_OUT ;
        GPIO_InitStructure.GPIO_OType=GPIO_OType_PP;
        GPIO_InitStructure.GPIO_PuPd=GPIO_PuPd_NOPULL;
        GPIO_Init(GPIOB, &GPIO_InitStructure);
}

static void SPI_Mode_Configuration(void)
{
        SPI_InitTypeDef  SPI_InitStructure;

        RCC_APB1PeriphClockCmd(RCC_APB1Periph_SPI2, ENABLE);
        SPI_I2S_DeInit(SPI2);

        SPI_InitStructure.SPI_Direction = SPI_Direction_2Lines_FullDuplex;
        SPI_InitStructure.SPI_DataSize = SPI_DataSize_8b;
        SPI_InitStructure.SPI_CPOL = SPI_CPOL_High;
        SPI_InitStructure.SPI_CPHA = SPI_CPHA_2Edge;
        SPI_InitStructure.SPI_NSS = SPI_NSS_Soft;
        SPI_InitStructure.SPI_BaudRatePrescaler = SPI_BaudRatePrescaler_256;
        SPI_InitStructure.SPI_FirstBit = SPI_FirstBit_MSB;
        SPI_InitStructure.SPI_CRCPolynomial = 7;
        SPI_InitStructure.SPI_Mode = SPI_Mode_Master;
        SPI_Init(SPI2, &SPI_InitStructure);
        SPI_Cmd(SPI2, ENABLE);
}
从机配置1(stm32f1)
void SPI1_Init(void)
{
        GPIO_InitTypeDef GPIO_InitStructure;
  
        RCC_APB2PeriphClockCmd(        RCC_APB2Periph_GPIOA|RCC_APB2Periph_SPI1, ENABLE );        

        GPIO_InitStructure.GPIO_Pin = GPIO_Pin_4|GPIO_Pin_5 | GPIO_Pin_6 | GPIO_Pin_7;
        GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
        GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
        GPIO_Init(GPIOA, &GPIO_InitStructure);

         GPIO_SetBits(GPIOA,GPIO_Pin_4|GPIO_Pin_5|GPIO_Pin_6|GPIO_Pin_7);

        SPI_InitStructure.SPI_Direction = SPI_Direction_2Lines_FullDuplex;
        SPI_InitStructure.SPI_Mode = SPI_Mode_Slave;
        SPI_InitStructure.SPI_DataSize = SPI_DataSize_8b;
        SPI_InitStructure.SPI_CPOL = SPI_CPOL_High;
        SPI_InitStructure.SPI_CPHA = SPI_CPHA_2Edge;
        SPI_InitStructure.SPI_NSS = SPI_NSS_Hard;
        SPI_InitStructure.SPI_BaudRatePrescaler = SPI_BaudRatePrescaler_256;
        SPI_InitStructure.SPI_FirstBit = SPI_FirstBit_MSB;
        SPI_InitStructure.SPI_CRCPolynomial = 7;
        SPI_Init(SPI1, &SPI_InitStructure);
        SPI_Cmd(SPI1, ENABLE);
}   
从机配置2(stm32f4)
static void SPI_GPIO_Configuration(void)
{
        GPIO_InitTypeDef GPIO_InitStructure;

        RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOB ,ENABLE);
        RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOC ,ENABLE);
        GPIO_StructInit(&GPIO_InitStructure);

        GPIO_InitStructure.GPIO_Pin = GPIO_Pin_12|GPIO_Pin_13 | GPIO_Pin_14 | GPIO_Pin_15;
        GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;
        GPIO_InitStructure.GPIO_OType = GPIO_OType_OD;//GPIO_OType_PP;
        GPIO_InitStructure.GPIO_PuPd  = GPIO_PuPd_UP;
        GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
        GPIO_Init(GPIOB, &GPIO_InitStructure);

        GPIO_PinAFConfig(GPIOB, GPIO_PinSource12, GPIO_AF_SPI2);
        GPIO_PinAFConfig(GPIOB, GPIO_PinSource13, GPIO_AF_SPI2);
        GPIO_PinAFConfig(GPIOB, GPIO_PinSource14, GPIO_AF_SPI2);
        GPIO_PinAFConfig(GPIOB, GPIO_PinSource15, GPIO_AF_SPI2);
        
        GPIO_SetBits(GPIOB,GPIO_Pin_12|GPIO_Pin_13|GPIO_Pin_14|GPIO_Pin_15);

        GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6| GPIO_Pin_7 | GPIO_Pin_8| GPIO_Pin_9;
        GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;
        GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;
        GPIO_InitStructure.GPIO_PuPd  = GPIO_PuPd_UP;
        GPIO_InitStructure.GPIO_Speed = GPIO_Speed_2MHz;
        GPIO_Init(GPIOC, &GPIO_InitStructure);
}

static void SPI_Mode_Configuration(void)
{
        SPI_InitTypeDef  SPI_InitStructure;

        RCC_APB1PeriphClockCmd(RCC_APB1Periph_SPI2, ENABLE);
        SPI_I2S_DeInit(SPI2);
        SPI_InitStructure.SPI_Direction = SPI_Direction_2Lines_FullDuplex;
        SPI_InitStructure.SPI_DataSize = SPI_DataSize_8b;
        SPI_InitStructure.SPI_CPOL = SPI_CPOL_High;
        SPI_InitStructure.SPI_CPHA = SPI_CPHA_2Edge;
        SPI_InitStructure.SPI_NSS = SPI_NSS_Hard;//SPI_NSS_Hard;//SPI_NSS_Soft;
        SPI_InitStructure.SPI_BaudRatePrescaler = SPI_BaudRatePrescaler_256;
        SPI_InitStructure.SPI_FirstBit = SPI_FirstBit_MSB;
        SPI_InitStructure.SPI_CRCPolynomial = 7;
        SPI_InitStructure.SPI_Mode = SPI_Mode_Slave;//SPI_Mode_Master;
        SPI_Init(SPI2, &SPI_InitStructure);
        SPI_Cmd(SPI2, ENABLE);
}


沙发
KC_CEC|  楼主 | 2014-4-11 16:22 | 只看该作者
本帖最后由 KC_CEC 于 2014-4-11 16:25 编辑

下面是主机测试程序(stm32f4)
while(1)
        {
                printf("************************************\r\n");
                printf("select the stm32f1..........\r\n");
                SPI_Send(0xf1);
                printf("now send stm32f1  data:0xf1........\r\n");
                printf("read stm32f1 data=%#X\r\n",SPI_Send(0xff));
                SPI_Send(0xf2);
                printf("now send stm32f1 data:0xf2........\r\n");
                printf("read stm32f1 data=%#X\r\n",SPI_Send(0xff));
                printf("************************************\r\n");
                printf("select the stm32f4..........\r\n");
                SPI_Send(0x11);
                printf("now send stm32f4  data:0x11........\r\n");
                printf("read stm32f4 data==%#X\r\n",SPI_Send(0xff));
                SPI_Send(0x12);
                printf("now send stm32f4 data:0x12........\r\n");
                printf("read stm32f4 data==%#X\r\n",SPI_Send(0xff));
                printf("************************************\r\n");
                SysTick_DelayMS(1000);
                printf("\r\n");
                printf("\r\n");
                printf("\r\n");
        }
实际上从机返回:
f1依次返回:0xf1,0xf2
f4依次返回:0x11,0x12

使用特权

评论回复
板凳
airwill| | 2014-4-11 20:42 | 只看该作者
中间电平在1.2V的样子!

说明其中应该存在问题. 硬件上有没有上拉电阻, 是不是拉得太厉害, 另外从机的 IO 口设置 GPIO_Speed_2MHz 适当加大.

使用特权

评论回复
地板
KC_CEC|  楼主 | 2014-4-14 10:09 | 只看该作者
airwill 发表于 2014-4-11 20:42
中间电平在1.2V的样子!

说明其中应该存在问题. 硬件上有没有上拉电阻, 是不是拉得太厉害, 另外从机的 IO  ...

外部硬件没有上拉,直通方式的。SPI的速度已经256分频了。就是42M/256约为164K 所以从机2M的反转速度已经够了哦。
我试了一下用FPGA读取电平,果然会将MISO的中间电平随机的读为高或者低。
然后,我干脆主机模拟SPI,FPGA读取的电平就稳定了

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

20

主题

169

帖子

1

粉丝