STM32/STM8技术william hill官网
直播中

1563661808

10年用户 1833经验值
擅长:电源/新能源
私信 关注
[讨论]

【高手问答】第5期——STM32硬件问答 

`

STM32硬件问答

高手问答第5期


小编导读:

      本期高手问答(7月28~8月4日)我们请来了@1402609807为大家解答关于STM32硬件方面的问题。

杜工简介:
       杜工是一个不怎么爱说话工程师,但是这样子,一点都不妨碍知识的分享、传播与交流。精通STM32,是一个航模DIY爱好者,现在从事的是电源电池方面的设计工作。

高手问答的意义:

      一如往期,是为了更好的促进大家有效的交流,为了让坛友提出的问题得到高手们的解答,用你提问的艺术引起高手们的关注提问的智慧!!!!提问必看

大牛在等着你,你还在等什么!!!
1、你还在为有关STM32的硬件问题发愁嘛?
2、你还有哪些想问但不敢问的问题嘛?

      如果你想得到高手们的思路提示或者与高手们探讨技术难点,那抢楼留言吧!留下你的问题,让智慧传播的更快更广。

      Elecfans高手问答一贯的风格,不欢迎任何与主题无关的讨论和喷子。
     下面欢迎大家就硬件威廉希尔官方网站 设计方面问题向@1402609807提问,请直接在回帖中提问。


社区高手招募
     不限专业领域、不限技术方向,只要你是一个有活力并乐于分享的开发者,只要你愿意把自己的经验收获分享给大家,帮助众多从业者共同学习、共同进步,我们就欢迎你来做客社区高手问答。
      联系方式:pengjiali@elecfans.com。快来联系小编吧!

***********************问答精华*****************************

` 杜工.jpg

回帖(43)

小麦地

2014-7-28 13:07:28

就是SD_PowerON那个函数下,他写的发送完cmd0,然后发送cmd8/*---------------------cmd8------*/

SDIO_CmdInitStructure.SDIO_Argument = SD_CHECK_PATTERN;        
  SDIO_CmdInitStructure.SDIO_CmdIndex = SDIO_SEND_IF_COND;        //CMD8
  SDIO_CmdInitStructure.SDIO_Response = SDIO_Response_Short;         
  SDIO_CmdInitStructure.SDIO_Wait = SDIO_Wait_No;                                                         
  SDIO_CmdInitStructure.SDIO_CPSM = SDIO_CPSM_Enable;
  SDIO_SendCommand(&SDIO_CmdInitStructure);
   errorstatus = CmdResp7Error();
        

  if (errorstatus == SD_OK)                  
  {
        
    CardType = SDIO_STD_CAPACITY_SD_CARD_V2_0;
    SDType = SD_HIGH_CAPACITY;        
  }
  else        
  {
         
    SDIO_CmdInitStructure.SDIO_Argument = 0x00;
    SDIO_CmdInitStructure.SDIO_CmdIndex = SD_CMD_APP_CMD;
    SDIO_CmdInitStructure.SDIO_Response = SDIO_Response_Short;
    SDIO_CmdInitStructure.SDIO_Wait = SDIO_Wait_No;
    SDIO_CmdInitStructure.SDIO_CPSM = SDIO_CPSM_Enable;
    SDIO_SendCommand(&SDIO_CmdInitStructure);
    errorstatus = CmdResp1Error(SD_CMD_APP_CMD);
  }
/*--------CMD55------------------------------------------------------------------------*/         
  SDIO_CmdInitStructure.SDIO_Argument = 0x00;
  SDIO_CmdInitStructure.SDIO_CmdIndex = SD_CMD_APP_CMD;
  SDIO_CmdInitStructure.SDIO_Response = SDIO_Response_Short;
  SDIO_CmdInitStructure.SDIO_Wait = SDIO_Wait_No;
  SDIO_CmdInitStructure.SDIO_CPSM = SDIO_CPSM_Enable;
  SDIO_SendCommand(&SDIO_CmdInitStructure);
        
        
  errorstatus = CmdResp1Error(SD_CMD_APP_CMD);        
/***下面是循环发送CMD55+acmd41********************************************************/



求大神指点,cmd8发送之后如果返回不是SD_OK为什么要发送cmd55,返回正确也要发送CMD55,我看协议说CMD55是为了表征下一个命令是ACMD,但是循环开始后也发送CMD55+ACMD。。这里的有什么用,求@1402609807 指点
举报

木頭瓶子

2014-7-28 13:12:55
uCGUI的GUI_SetDrawMode()函数设置显示不正常
我的GUI库是3.9版本的。我在测试GUI_SetDrawMode()函数的时候,对着GUI的中文手册上的步骤去写,但粗来的效果跟手册的效果截然不同的呢。效果如图,好像有残影似的,这是什么原因呢?@1402609807




1 举报

二霸

2014-7-28 14:21:19
目前正在调试的设备连上主机后,没有通信,一开始以为是硬件的问题,后来测了一下电压和波形,发现都正常,软件中CAN模块已经初始化了,问题是不能进入中断,下面是中断部分的代码:        NVIC_InitStructure.NVIC_IRQChannel = USB_LP_CAN1_RX0_IRQn;
        NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;
        NVIC_InitStructure.NVIC_IRQChannelSubPriority = 1;
        NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
        NVIC_Init(&NVIC_InitStructure);

在中断处理文件中,
void USB_LP_CAN1_RX0_IRQHandler(void)
{
        CAN_GetData();
}
这个函数没有被编译。而且,如果连上主机再上电或DEBUG,程序会卡死在中断代码的最后一步
@1402609807 解答,多谢
举报

香脆面

2014-7-28 14:30:27
过配置 ARR=0xfffff PSC=72-1.
也就是1M捕获


当我去测15HZ到50KHZ 时候,测出来数据没有问题,精度也差不多在1%。
问题是 当频率达到50KHZ以上的时候,根本无法测量,频率跳变,检测出来的数字还很奇怪
66666HZ .等等
理论上不是1M捕获 最大能测1M 最小15HZ吗 为什么我就测不出来,!!!急死我了!!


void TIM4_PWMINPUT_INIT(u16 arr,u16 psc)
{

TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;
NVIC_InitTypeDef NVIC_InitStructure;
TIM_ICInitTypeDef TIM4_ICInitStructure;
GPIO_InitTypeDef GPIO_InitStructure;

RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM4, ENABLE); //Open TIM4 clock
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB, ENABLE); //open gpioB clock

GPIO_InitStructure.GPIO_Pin = GPIO_Pin_7; //GPIO??
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOB, &GPIO_InitStructure);

TIM_TimeBaseStructure.TIM_Period = arr; //设置在下一个更新事件装入活动的自动重装载寄存器周期的值
TIM_TimeBaseStructure.TIM_Prescaler =psc; //设置用来作为TIMx时钟频率除数的预分频值
TIM_TimeBaseStructure.TIM_ClockDivision = 0; //设置时钟分割:TDTS = Tck_tim
TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up; //TIM向上计数模式
TIM_TimeBaseInit(TIM4, &TIM_TimeBaseStructure); //根据TIM_TimeBaseInitStruct中指定的参数初始化TIMx的时间基数单位


/*配置中断优先级*/
NVIC_InitStructure.NVIC_IRQChannel = TIM4_IRQn;
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 1;
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
NVIC_Init(&NVIC_InitStructure);

TIM4_ICInitStructure.TIM_Channel = TIM_Channel_2;
TIM4_ICInitStructure.TIM_ICPolarity = TIM_ICPolarity_Rising;
TIM4_ICInitStructure.TIM_ICSelection = TIM_ICSelection_DirectTI;
TIM4_ICInitStructure.TIM_ICPrescaler = TIM_ICPSC_DIV1;
TIM4_ICInitStructure.TIM_ICFilter = 0x0;

TIM_PWMIConfig(TIM4, &TIM4_ICInitStructure); //PWM输入配置
TIM_SelectInputTrigger(TIM4, TIM_TS_TI2FP2); //选择有效输入端
TIM_SelectSlaveMode(TIM4, TIM_SlaveMode_Reset); //配置为主从复位模式
TIM_SelectMasterSlaveMode(TIM4, TIM_MasterSlaveMode_Enable);
TIM_ITConfig(TIM4, TIM_IT_CC2|TIM_IT_Update, ENABLE); //中断配置
TIM_ClearITPendingBit(TIM4, TIM_IT_CC2|TIM_IT_Update); //清除中断标志位
TIM_Cmd(TIM4, ENABLE);
}
u16 period = 0;
u16 duty = 0;
u8 CollectFlag = 1;
void TIM4_IRQHandler(void)
{
if(CollectFlag){
if (TIM_GetITStatus(TIM4, TIM_IT_CC2) != RESET)//捕获1发生捕获事件
{
duty = TIM_GetCapture1(TIM4); //采集占空比
period=TIM_GetCapture2(TIM4); //采集周期
}
}
TIM_ClearITPendingBit(TIM4, TIM_IT_CC2|TIM_IT_Update); //清除中断标志位
}
麻烦@1402609807帮忙看看
举报

我有一车切糕

2014-7-29 10:59:01
我用51单片机NRF2401与STM32的NRF2401通讯,,51单片机的作为发送芯片;STM32的作为接收芯片,但是接收打开后很久才能接收到数据并且是乱码,求解答这是什么原因???麻烦@1402609807 帮忙看看
举报

泡芙奶昔

2014-7-29 11:01:14
大神求教:stm8在PWM捕获时,是如何用多个采样验证一个边沿转换的?时间来得及吗?这个过程为什么叫滤波?
CCMR2中IC1F[3:0]和IC1PSC[1:0]作用到底是什么?
因为我担心他的采样频率低于我的PWM输入信号,到时候采到的是错误值。所以由此一问。谢谢!!!
看到一篇文章里面说:“假设输入信号在最多5个时钟周期的时间内抖动,我们须配置滤波器的带宽长于5个时钟周期;因此我们可以连续采样8次,以确认在TI1上一次真实的边沿变换,”
请问:他的意思是指在“TI1上一次真实的边沿变换(即输入信号的抖动)持续时间最多在5个时钟周期,而stm8会在 “每个时钟周期采样一次”,于是这里让它采样大于5个时钟周期的8个时钟周期,如果这段时间输入信号确实发生边沿转换了,那么,采样到的8个相同的信息,可以确认这次输入信号的转换”

我这样理解对吗?我觉得每个时钟周期采样一次是不是不太可能?@1402609807 求教
举报

niu!kf

2014-7-29 16:32:59

想购买stm32开发板,淘宝好点的都500多了,哪里可以买到300左右的好点的开发板!
举报

hxjq

2014-7-29 16:38:26
你好,设计一个鼠标用哪些芯片啊,
控制芯片用哪种好,图像传感器,u***协议都需要哪些芯片呢?
举报

surround

2014-7-29 16:39:53
FCARM - Output Name not specified, please check 'Options for Target - Utilities'
这是错误提示   不知道该怎么配置Options for Target - Utilities选项卡   求大神  求解救
举报

rosa

2014-7-29 16:43:18
FSMC要怎么配置啊?驱动2.8寸的TFT一定要用FSMC吗?我查了好资料还是一头雾水。我就一菜鸟,请大神们帮帮忙?
举报

笔画张

2014-7-29 16:44:38

大神好,stm32怎么控制编码器,让编码器记录电机的转数呢?
举报

麦特拉布

2014-7-29 16:46:10
串行通信中的位间隔指的 是什么    各位之间的距离是位间隔的整数倍 怎么理解  求大神科普
举报

douyin8

2014-7-29 16:49:18

我是新手。 自己画了一个pcb,如图

中间那个是从altium界面那里选取的带加号的电容(电解电容?),右边的是stm32f407,可是这个电容为何这么大? 我看别人的板子上面电容都和芝麻一样大啊 222222222222222222222222222.jpg

举报

tulin

2014-7-29 16:51:18
大神有没有做过将STM32保存图片到SD的??感激不尽
举报

insistdream2013

2014-7-29 17:40:31
大神 你好 请问一般基于STM32周期的项目 一般要做多久呢
举报

1402609807

2014-7-29 17:41:01
引用: douyin8 发表于 2014-7-29 16:49
我是新手。 自己画了一个pcb,如图

中间那个是从altium界面那里选取的带加号的电容(电解电容?),右边 ...


你用的是封装和别人的不一样,那芝麻小的有0201 0402 0603 0805 等,这些都是贴片,功率各不一样,你的那个是直插的电容,去搜着看一下电容的分类和封装,村田,三星,都出电容 和电阻,磁珠 电感之类的。
举报

1402609807

2014-7-29 17:42:41
引用: rosa 发表于 2014-7-29 16:43
FSMC要怎么配置啊?驱动2.8寸的TFT一定要用FSMC吗?我查了好资料还是一头雾水。我就一菜鸟,请大神们帮帮忙 ...


可以不用,用FSMC快些,你可以去参考一下野火、战舰的程序~去买(借)本书~
举报

我是大彭

2014-7-30 09:49:17
引用: tulin 发表于 2014-7-29 16:51
大神有没有做过将STM32保存图片到SD的??感激不尽

//BMP编码函数
//将当前LCD屏幕的指定区域截图,存为16位格式的BMP文件 RGB555格式.
//保存为rgb565则需要掩码,需要利用原来的调色板位置增加掩码.这里我们已经增加了调色板.
//保存为rgb555格式则需要颜色转换,耗时间比较久,所以保存为565是最快速的办法.
//filename:存放路径
//x,y:在屏幕上的起始坐标   
//mode:模式.0,仅仅创建新文件的方式编码;1,如果之前存在文件,则覆盖之前的文件.如果没有,则创建新的文件.
//返回值:0,成功;其他,错误码.   
u8 bmp_encode(u8 *filename,u16 x,u16 y,u16 width,u16 height,u8 mode)
{       
FIL* f_bmp;
u16 bmpheadsize;         //bmp头大小                  
        BITMAPINFO hbmp;         //bmp头          
u8 res=0;
u16 tx,ty;                    //图像尺寸
u16 *databuf;         //数据缓存区地址                  
u16 pixcnt;                    //像素计数器
u16 bi4width;                        //水平像素字节数            
if(width==0||height==0)return PIC_WINDOW_ERR;        //区域错误
if((x+width-1)>LCD_W)return PIC_WINDOW_ERR;         //区域错误
if((y+height-1)>LCD_H)return PIC_WINDOW_ERR;        //区域错误  
          
#if BMP_USE_MALLOC == 1        //使用malloc       
databuf=(u16*)mymalloc(SRAMIN,1024);         //开辟至少bi4width大小的字节的内存区域 ,对240宽的屏,480个字节就够了.
if(databuf==NULL)return PIC_MEM_ERR;         //内存申请失败.
f_bmp=(FIL *)mymalloc(SRAMIN,sizeof(FIL));        //开辟FIL字节的内存区域  
if(f_bmp==NULL)         //内存申请失败.
{          
myfree(SRAMIN,databuf);
return PIC_MEM_ERR;       
}           
#else
databuf=(u16*)bmpreadbuf;
f_bmp=&f_bfile;
#endif               
bmpheadsize=sizeof(hbmp);//得到bmp文件头的大小   
gui_memset((u8*)&hbmp,0,sizeof(hbmp));//置零空申请到的内存.             
hbmp.bmiHeader.biSize=sizeof(BITMAPINFOHEADER);//信息头大小
hbmp.bmiHeader.biWidth=width;                 //bmp的宽度
hbmp.bmiHeader.biHeight=height;         //bmp的高度
hbmp.bmiHeader.biPlanes=1;                  //恒为1
hbmp.bmiHeader.biBitCount=16;                 //bmp为16位色bmp
hbmp.bmiHeader.biCompression=BI_BITFIELDS;                 //bmp为16位色bmp
        hbmp.bmiHeader.biSizeImage=hbmp.bmiHeader.biHeight*hbmp.bmiHeader.biWidth*hbmp.bmiHeader.biBitCount/8;//bmp数据区大小
             
hbmp.bmfHeader.bfType=((u16)'M'<<8)+'B';//BM格式标志
hbmp.bmfHeader.bfSize=bmpheadsize+hbmp.bmiHeader.biSizeImage;//整个bmp的大小
           hbmp.bmfHeader.bfOffBits=bmpheadsize;//到数据区的偏移

hbmp.RGB_MASK[0]=0X00F800;                 //bmp为16位色bmp
hbmp.RGB_MASK[1]=0X0007E0;                 //bmp为16位色bmp
hbmp.RGB_MASK[2]=0X00001F;                 //bmp为16位色bmp

if(mode==1)res=f_open(f_bmp,(const TCHAR*)filename,FA_READ|FA_WRITE);//尝试打开之前的文件
        if(mode==0||res==0x04)res=f_open(f_bmp,(const TCHAR*)filename,FA_WRITE|FA_CREATE_NEW);//模式0,或者尝试打开失败,则创建新文件             
        if((hbmp.bmiHeader.biWidth*2)%4)//水平像素(字节)不为4的倍数
{
bi4width=((hbmp.bmiHeader.biWidth*2)/4+1)*4;//实际要写入的宽度像素,必须为4的倍数.       
}else bi4width=hbmp.bmiHeader.biWidth*2;//刚好为4的倍数          
        if(res==FR_OK)//创建成功
{
res=f_write(f_bmp,(u8*)&hbmp,bmpheadsize,&bw);//写入BMP首部   
for(ty=y+height-1;hbmp.bmiHeader.biHeight;ty--)
{
pixcnt=0;
         for(tx=x;pixcnt!=(bi4width/2);)
{
if(pixcnt else databuf[pixcnt]=0Xffff;//补充白色的像素.   
pixcnt++;
tx++;
}
hbmp.bmiHeader.biHeight--;
res=f_write(f_bmp,(u8*)databuf,bi4width,&bw);//写入数据
}
f_close(f_bmp);
}             
#if BMP_USE_MALLOC == 1        //使用malloc       
myfree(SRAMIN,databuf);          
myfree(SRAMIN,f_bmp);          
#endif       
return res;
}



>
//BMP信息头
typedef __packed struct
{
    u32 biSize ;                    //说明BITMAPINFOHEADER结构所需要的字数。
    long  biWidth ;                    //说明图象的宽度,以象素为单位  
    long  biHeight ;                   //说明图象的高度,以象素为单位  
    u16  biPlanes ;                    //为目标设备说明位面数,其值将总是被设为1  
    u16  biBitCount ;                   //说明比特数/象素,其值为1、4、8、16、24、或32
    u32 biCompression ;          //说明图象数据压缩的类型。其值可以是下述值之一:
//BI_RGB:没有压缩;
//BI_RLE8:每个象素8比特的RLE压缩编码,压缩格式由2字节组成(重复象素计数和颜色索引);   
    //BI_RLE4:每个象素4比特的RLE压缩编码,压缩格式由2字节组成
          //BI_BITFIELDS:每个象素的比特由指定的掩码决定。
    u32 biSizeImage ;         //说明图象的大小,以字节为单位。当用BI_RGB格式时,可设置为0   
    long  biXPelsPerMeter ;        //说明水平分辨率,用象素/米表示
    long  biYPelsPerMeter ;        //说明垂直分辨率,用象素/米表示
    u32 biClrUsed ;                           //说明位图实际使用的彩色表中的颜色索引数
    u32 biClrImportant ;         //说明对图象显示有重要影响的颜色索引的数目,如果是0,表示都重要。  
}BITMAPINFOHEADER ;
//BMP头文件
typedef __packed struct
{
    u16  bfType ;     //文件标志.只对'BM',用来识别BMP位图类型
    u32  bfSize ;          //文件大小,占四个字节
    u16  bfReserved1 ;//保留
    u16  bfReserved2 ;//保留
    u32  bfOffBits ;  //从文件开始到位图数据(bitmap data)开始之间的的偏移量
}BITMAPFILEHEADER ;
//彩色表  
typedef __packed struct  
{
    u8 rgbBlue ;    //指定蓝色强度
    u8 rgbGreen ;        //指定绿色强度  
    u8 rgbRed ;                  //指定红色强度  
    u8 rgbReserved ;//保留,设置为0  
}RGBQUAD ;
//位图信息头
typedef __packed struct
{  
BITMAPFILEHEADER bmfHeader;
BITMAPINFOHEADER bmiHeader;   
u32 RGB_MASK[3];         //调色板用于存放RGB掩码.
//RGBQUAD bmiColors[256];   
}BITMAPINFO;  
typedef RGBQUAD * LPRGBQUAD;//彩色表   

//图象数据压缩的类型
#define BI_RGB                  0  //没有压缩.RGB 5,5,5.
#define BI_RLE8          1  //每个象素8比特的RLE压缩编码,压缩格式由2字节组成(重复象素计数和颜色索引);
#define BI_RLE4          2  //每个象素4比特的RLE压缩编码,压缩格式由2字节组成
#define BI_BITFIELDS         3  //每个象素的比特由指定的掩码决定。   
        
//////////////////////////////////////////////////
仅供参考


举报

我是大彭

2014-7-30 09:53:37
引用: hxjq 发表于 2014-7-29 16:38
你好,设计一个鼠标用哪些芯片啊,
控制芯片用哪种好,图像传感器,u***协议都需要哪些芯片呢? ...

可以参考  http://wenku.baidu.com/view/967528fc700abb68a982fb7d
举报

更多回帖

发帖
×
20
完善资料,
赚取积分