深入解析STM32_USB-FS-Device_Lib库V0.2

发布者:HarmoniousDream最新更新时间:2020-11-10 来源: eefocus关键字:STM32  USB-FS-Device  Lib库 手机看文章 扫描二维码
随时随地手机看文章

图1 展示了一个典型的USB应用与USB-FS-Device library的关系图。我们可以看出图中由3个层构成分别是:外围硬件(hardware)、STM32_USB-FS_Device_Lib和用户层(User application)。我们从下到上来分析:

 

 图1 典型的USB应用与USB-FS-Device library的关系图

 

1.外围硬件(hardware)

     就是我们的购买的芯片STM32F10XXX和开发板

2  STM32_USB-FS_Device_Lib

就是STM提供给我们的The USB-FS-Device library固件库,它由STM32_USB FS_Device_ Driver和Application Interface layer两个部分组成。

其中STM32_USB-FS_Device_Driver这层管理USB的硬件设备和USB标准协议的直接交互,它又由Low Layer 和 Medium Layer两个层组成;Application Interface layer-High Layer这层又叫High Layer层,它在固件库核和应用提供给用户一个完整的接口。

图2 是我给出的STM32_USB-FS-Device_Lib_V3.1.0 结构图,下面我们将对这个整个结构的运行机理分析,然后结构逐层给出具体含义。

 

 

 


 


 图2 STM32_USB-FS-Device_Lib_V3.1.0 结构图


 

    和其他的接口一样,当受到USB的中断后,进入stm32f10x_it.c中的USB_LP_CAN1_RX0

_IRQHandler()和USB_HP_CAN1_TX_IRQHandler()中断服务子程序。其中优先级高的由USB_HP_CAN1_TX_IRQHandler处理,优先级低的由USB_LP_CAN1_RX0_ IRQHandler处理。

    对于USB_HP_CAN1_TX_IRQHandler函数,它直接调用usb_int (.h , .c)中的CTR_HP(),然后根据发送和接受数据,它调用usb_endp(.c)中的EPX_IN_Callback()或EPX_OUT_ Callback()函数。对于EPX_IN_Callback和EPX_OUT_Callback()这14个函数(X=1,2...7)它们在usb_conf(.h)中通过

#define  EPX_IN_Callback   NOP_Process

#define  EPX_OUT_Callback   NOP_Process

的形式,来由用户决定是否提供具体的实现并调用。而将它们和CTR_HP联系在一起的操作,在usb_istr(.h,.c)中以下面的形式给出:

void (*pEpInt_IN[7])(void) ={

    EP1_IN_Callback,

    ...

    EP7_IN_Callback,};

void (*pEpInt_OUT[7])(void) ={

    EP1_OUT_Callback,

    ...

EP7_OUT_Callback,};

对于USB_HP_CAN1_TX_IRQHandler函数,它直接调用usb_istr(.h,.c)中的USB_Istr(),USB_Istr()根据具体的请求决定是调用usb_istr(.h,.c)中下面函数

void CTR_Callback(void);

void DOVR_Callback(void);

void ERR_Callback(void);

void WKUP_Callback(void);

void SUSP_Callback(void);

void RESET_Callback(void);

void SOF_Callback(void);

void ESOF_Callback(void);

还是调用usb_int(.h,.c)中的void CTR_LP(void)。对于上面的这个函数是否给出定义,是由用户在usb_conf(.h)中,通过下面的宏决定的

/*#define CTR_CALLBACK*/

/*#define DOVR_CALLBACK*/

/*#define ERR_CALLBACK*/

/*#define WKUP_CALLBACK*/

/*#define SUSP_CALLBACK*/

/*#define RESET_CALLBACK*/

#define SOF_CALLBACK

/*#define ESOF_CALLBACK*/

如果调用了 CTR_LP()函数,CTR_LP()函数中如果不是端点0的请求,则和CTR_LP一样的顺序处理;如果是端点0,它调用usb_core(.h,.c)中的

uint8_t Setup0_Process(void);

uint8_t Post0_Process(void);

uint8_t Out0_Process(void);

uInt8_t In0_Process(void);

如果是标准的请求,便调用usb_core(.h,.c)中的下面的函数

RESULT Standard_SetEndPointFeature(void);

RESULT Standard_SetDeviceFeature(void);

uint8_t *Standard_GetConfiguration(uint16_t Length);

RESULT Standard_SetConfiguration(void);

uint8_t *Standard_GetInterface(uint16_t Length);

RESULT Standard_SetInterface(void);

Uint8_t *Standard_GetDescriptorData(uint16_t ...);

uint8_t *Standard_GetStatus(uint16_t Length);

RESULT Standard_ClearFeature(void);

void SetDeviceAddress(uint8_t);

这些函数,又调用USER_STANDARD_REQUESTS结构指定的中,用户在usb_prop(.h,.c)中定义的函数。如果不是标准请求,则调用DEVICE_PROP结构指定的中,用户在usb_prop(.h,.c)中定义的函数其他一些函数。

 

 


 下面我再按文件分析一次:

 

 

usb_conf.h

usb_conf.h中的#define IMR_MSK (CNTR_CTRM  | CNTR_SOFM  | CNTR_RESETM )来决定USB_CNTR寄存器中的那个USB相关中断启动还是屏蔽。

 

usb_istr.c

进入USB_Istr()后,首先检测是否是CTR位中断,即完成一次数据的正处传输,如果是,并且相应IMR_MSK没有屏蔽,就调用usb_int,c中的CTR_LP()函数,如果定义了CTR_CALLBACK,则调用本文件中定义的CTR_Callback()函数。

然后检测是否是RESET位中断,如果是,并且相应的中断没有屏蔽,则首先清楚USB_ISTR寄存中相应的中断位,然后调用用户在usb_prop.c的Device_Property结构体中填充的相应的函数;如果定义了宏RESET_CALLBACK还将调用本文件中定义的RESET_Callback()函数。

其他的类似。

 

注意:值得我们注意的是如果缓冲区的数据溢出,则不会调用 CTR_LP()和CTR_Callback(),这样的话,我们也就没有机会来处理这些数据,所以,如果你想处理缓冲区溢出时的数据你必须定义DOVR_CALLBACK,并提供DOVR_Callback()函数。

 

usb_int.h

    进入CTR_LP()函数后,首先检测发生中断断点的ID如果是端点0,则根据是输入还是输出调用。如果是IN,则调用usb_core(.h,.c)中的In0_Process()函数;否则检测是否是SETUP,是的话调用usb_core(.c)中的Setup0_Process()函数,不是的话调用usb_core(c)中的Out0_Process()函数。如果不是端点0则调用usb_endp(.c)中 EPX_IN_Callback()和EPX_OUT_Callback()。

进入CTR_HP()后,因为它只接受同步传输和双缓冲区的批量传输中的,所以它直接检测是IN还是OUT,并调用usb_endp(.c)中 EPX_IN_Callback()和EPX_OUT_Callback()。

 

usb_core(.h,.c)

Setup0_Process()

    进入Setup0_Process()函数后,如果现在的CONTROL_STATE状态不是PAUSE则,填充pInformation指向的DEVICE_INFO结构体,然后设置CONTROL_STATE现在状态为SETTING_UP,然后根据数据的长度是否为0调用NoData_Setup0()或者 Data_Setup0()函数,最后调用Post0_Process()????????。

 

NoData_Setup0()

进入NoData_Setup0()后,首先判断是否接收者是设备并且是标准请求,如果是根据请求的类型SET_CONFIGURATION、SET_ADDRESS、SET_FEATURE和CLEAR_FEATURE来调用该文件中的相应函数;然后判断是否接收者是接口并且是标准请求,如果是根据是否是SET_INTERFACE来调用文件中相应的函数;其次判断是否接收者是端点并且是标准请求,如果是则根据CLEAR_FEATURE和SET_FEATURE来调用相应的本文件中函数。否则结果设置成USB_UNSUPPORT。

    接下来,如果结果是USB_UNSUPPORT,则调用usb_prop(.h,.c)中DEVICE_PROP结构体中填充的RESULT (*Class_NoData_Setup)(uint8_t RequestNo)函数,我们就在该函数中处理不是类库中已经实现的请求。

 

Data_Setup0()

进入Data_Setup0()后,首先检测请求代码是否是GET_DESCRIPTOR,如果是根据描述符的请求,分别调用usb_prop(.h,.c)中DEVICE_PROP结构体中填充的设备描述符、配置描述符和字符串描述符的函数;然后检测请求代码是否是GET STATUS,如果是则调用Standard_GetStatus函数;其次检测是否是GET_CONFIGURATION和GET_INTERFACE,如果是调用相关函数。

如果不满足上面条件则调用调用usb_prop(.h,.c)中DEVICE_PROP结构体中填充的RESULT (*Class_Data_Setup)(uint8_t RequestNo)函数,我们就在该函数中处理不是类库中已经实现的请求。

最后根据请求设置相应状态,用于下次通信。


关键字:STM32  USB-FS-Device  Lib库 引用地址:深入解析STM32_USB-FS-Device_Lib库V0.2

上一篇:USB通讯的执行过程 - STM32 USB设计
下一篇:SD卡升级——SDIO_IAP实验

推荐阅读最新更新时间:2024-11-10 20:20

IAR中创建STM32工程步骤(寄存器版本)
先说明,是基于寄存器编程的。 1.从官网下载STM32固件库。我用的是3.5 2.创建一个STM32文件夹(不是存放工程的),存放创建STM32工程所需的基本文件。以后再次创建工程时,只需把这个文件夹的东西拷到相应工程里面即可。 此文件夹里面有CMSIS文件夹和Statup文件夹。 2.找到解压后的Libraries- CMSIS- CoreSupport,把里面的core_cm3.h和core_cm3放进上面的CMSIS文件夹。 找到Libraries- CMSIS- DeviceSupport- ST- STM32F10X- Statup- IAR里面的启动文件,这个启动文件根据STM32具体类型选择,我用的是STM32
[单片机]
STM32 图像处理函式介绍
STM32 图像处理函式库介绍 STM32 图像处理函式库STM32IPL是由 C 语言所编写的开放原始码软件函式库,提供了图像处理和计算机视觉功能,能加快在意法半导体(ST)的STM32 微控制器上开发视觉分析的应用。本产品在最新版 (v3.1.0)FP-AI-VISION1 功能套件中以STM32Cube 中间件的形式推出。 一般来说,视觉深度学习模型的输入不同于相机拍摄的图像,深度学习输入因为具有不同维度及图像格式,会需要预先处理原图,例如缩放、影像格式转换和标准化等。而STM32IPL可提供实用且现成的软件套件,以简化及加速影像预处理功能的开发。 主要特色 STM32IPL的主要特色如下: -
[单片机]
<font color='red'>STM32</font> 图像处理函式<font color='red'>库</font>介绍
STM32自定义printf实现多串口互用
STM32 串口使用频繁的朋友可能知道一个问题,库自带的 USART_SendData 函数一次只能发送 1 Byte 字符 如果我们要输出一个带格式、带参数的串口数据就只能通过 sprintf 打印到一个临时数组,然后再使用一个for循环调用USART_SendData一个字符一个字符的输出,过程非常麻烦! 姜斌是一个非常怕麻烦的人所以这种方法无疑让我发疯!后来在原子(OpenEDV)那里购买了开发板拿到了例程。里面重定向了printf函数作为串口输出函数,有了这个函数之后就能够很轻松的参数输出,但问题就在这里我们串口1 串口2 都要带参数输出怎么办? 本次实验:自定义printf函数 实验数据来源: 配置usart
[单片机]
stm32上移植linux的实操案例经验分享
刚从硬件跳槽为嵌软时,没有任何一丝的准备。一入职,领导就交代了一项特难的任务——在stm32上移植linux! 瞬间我就懵了,没办法硬着头皮上吧,先搜集资料,我之前跑的是ok6410的板子上运行的linux,现在是在stm32上移植,以前stm32倒是玩过,研究生期间就捣鼓过它,但现在还没从抓烙铁的硬件当中缓过神来,就转到嵌入式软件的开发,更头疼的是stm32没有MMU!没有MMU!找了一下,好吧,有个uClinux! 于是开始学习各种相关的知识,了解到linux的启动一般是u-boot——》liunx内核——》根文件系统,那么首先要做个基于stm32的u-boot,先初始化时钟、外设、中断什么的,看了韦东山老师的视频感觉
[单片机]
<font color='red'>stm32</font>上移植linux的实操案例经验分享
STM32 SPI 收发数据 ---规则 + 问题解析
规则: 1) 高速同步串行口。3~4线接口(CS ,CLK ,MOSI,MISO),收发独立、可同步进行。 2)SPI分为主从模式,主模式提供时钟和片选选择信号. 3) 模式控制:CPOL用来控制时钟信号(clk)在空闲时候的状态;CPHA用来控制采样时刻时CLK的边缘动作。 CPOL CPHA 模式: 0 0 CLK空闲时为低电平,CLK上升沿采样数据。 0 1 CLK空闲为低电平,CLK下降沿采样数据。 1 0 CLK空闲时为高电平,CLK上升沿采样数据。 1 1 CLK空闲时为高电平,CLK下降沿采样数据。 1)SPI配置(3.01库): SPI_InitStructure.SPI_Direction = SPI_D
[单片机]
STM32ADC中断的使用注意事项和优化建议
STM32ADC(模拟数字转换器)是STMicroelectronics开发的一款用于外部模拟信号转换为数字信号的器件。在使用STM32ADC时,合理地使用中断是提高系统性能和精确度的关键。本文将详细介绍STM32ADC中断的使用注意事项和优化建议。 注意事项: 1. 合理选择中断触发方式:STM32ADC可以通过软件触发(软件启动转换模式)和硬件触发(定时器、外部事件等)两种方式进行转换。软件触发可以根据需要灵活控制转换,适用于一些特定场景;硬件触发方式可以提高系统的实时性和准确性,但对硬件和软件操作有一定要求。 2. 选择合适的ADC转换模式:STM32ADC提供了多种转换模式,包括单次转换模式、连续转换模式和注入转换模式等。
[单片机]
基于stm32单片机的模拟IIC时序
我下面要说的是基于stm32单片机的模拟IIC时序,以及是一些要注意的事项;结合自己所做的MMA7455加速度传感器,我把模拟IIC的源代码贴了出来,大家可以参考一下。 1.因为在IIC协议中,当总线空闲的时候,SDA和SCL都为高电平,所以硬件电路中SDA和SCL引脚都要接上拉电阻。 2.注意开始信号,停止信号,响应信号,非响应信号的时序,特别是要留意高低电平时间的延时: 3.应答信号分为主机应答和从机应答: 主机应答是在主机从从机中读取数据时每次读取完一个字节的数据后主机给从机的一个应答信号,表示主机已收到数据了。 从机应答是指主机给从机发送数据时从机给主机的应答,给一个应答就代表从机已经收到了数据,为主机
[单片机]
基于<font color='red'>stm32</font>单片机的模拟IIC时序
STM32时钟系统介绍与总结
时钟树: 1. HSI振荡器时钟 The HSI clock signal is generated from an internal 8 MHz RC Oscillator and can be used directly as a system clock or divided by 2 to be used as PLL input. The HSI RC oscillator has the advantage of providing a clock source at low cost (no external components). It also has a faster startup time than
[单片机]
小广播
设计资源 培训 开发板 精华推荐

最新单片机文章
何立民专栏 单片机及嵌入式宝典

北京航空航天大学教授,20余年来致力于单片机与嵌入式系统推广工作。

换一换 更多 相关热搜器件
更多往期活动

 
EEWorld订阅号

 
EEWorld服务号

 
汽车开发圈

电子工程世界版权所有 京B2-20211791 京ICP备10001474号-1 电信业务审批[2006]字第258号函 京公网安备 11010802033920号 Copyright © 2005-2024 EEWORLD.com.cn, Inc. All rights reserved