STM32

STM32是STMicroelectronics(意法半导体)推出的一系列基于ARM Cortex-M内核的32位微控制器(MCU)产品。这些微控制器提供了广泛的产品系列,覆盖了多种不同的性能和功能需求,适用于各种应用领域,包括工业控制、汽车电子、消费类电子、医疗设备等。

STM32系列微控制器以其高性能、低功耗、丰富的外设接口和灵活的开发工具而闻名。它们通常具有丰富的存储器、多种通信接口(如UART、SPI、I2C、CAN等)、模拟数字转换器(ADC)、定时器、PWM输出等功能,以满足不同应用场景下的需求。

STM32微控制器通常使用标准的ARM Cortex-M内核,包括Cortex-M0、M0+、M3、M4和M7等,这些内核具有不同的性能和功耗特性,可根据具体应用的需求进行选择。此外,STM32系列还提供了多种封装和引脚配置,以满足不同尺寸和集成度的要求。

STMicroelectronics为STM32系列提供了丰富的开发工具和支持资源,包括基于ARM开发环境的集成开发环境(IDE)、调试器、评估板和参考设计等。这些工具和资源有助于开发人员快速开发和部署他们的应用,并提供了全面的技术支持和文档资料,帮助用户充分发挥STM32微控制器的性能和功能优势。

X-Cube-Cryptolib V4

加解密算法是实现信息安全设计的重要工具,在安全启动,安全通信等多个场景都会用到,STM32一直以来都提供支持全系列的算法库软件包X-CUBE-CRYPTOLIB,今年STM32对其加解密算法库又做了进一步的改进升级,发布了V4版本,这个版本的主要亮点有哪些?

“新版STM32加解密算法库——X-Cube-Cryptolib

接下来我们具体看一下V4版本的加解密库有哪些新变化。

Cryptolib V4支持的算法

新增加的算法

“新版STM32加解密算法库——X-Cube-Cryptolib
  • 支持国密SM算法
    • SM4 (CBC, CFB, CTR, ECB, OFB)
    • SM3
    • SM2 (密钥对生成,计算ZA,签名,验签)
  • 散列算法
    • 除了SM3,还增加了SHA3 (SHA3-224, SHA3-256, SHA3-384, SHA3-512) 和SHAKE
  • MAC算法
    • HMAC (SM3), KMAC (SHAKE)
  • ECC椭圆曲线算法
    • 除了SM2,还增加了ECDSA的Ed448
  • ECDH算法
    • 增加Curve448
  • RSA算法
    • 新增加PKCS#1 V2.2 以及 RSA CRT模式(包含抵御Bellcore攻击的防护)
  • 随机数生成
    • 增加CTR_DRBG_AES256

不再包含的算法

软件包内容

新的软件包架构

新版本采用了新的软件包架构

  • 加解密库仅按照内核提供(每个内核对应一个加解密库)
  • 加解密库不再按照STM32系列分别提供
  • 加解密库不再区分编译器和优化方式(Speed、Size、FPU)

“新版STM32加解密算法库——X-Cube-Cryptolib

V4的目录结构 vs. V3的目录结构

V3软件包的目录结构是每一个STM32系列对应一个单独的目录

  • 每个芯片系列都有对应的Middleware目录, 里面包含加解密库
  • 加解密库有多个库文件,分别针对不同编译器以及不同的优化选项
  • 参考例程工程同样也在每个STM32系列子目录的Projects目录中。

“新版STM32加解密算法库——X-Cube-Cryptolib

V4的目录结构则完全兼容Cube/X-Cube软件包(STM32Cubexx / X-Cube-xxx)架构,方便与Cube/X-Cube包进行集成。

  • V4中包含加解密库的Middleware文件夹直接在顶层目录
  • lib目录下的库文件不针对每个STM32系列,也不再区分不同的编译器和优化方式
  • 加解密库文件按照Cortex内核版本,每个内核提供一个统一的库文件
  • 同一个库文件可以适用于各种编译器(AEABI兼容)
  • 对于不同优化选项的选择可以在链接阶段进行配置

“新版STM32加解密算法库——X-Cube-Cryptolib

V4的参考例程则类似Cube/X-Cube包的结构,在Projects目录下的各个系列的子目录中提供。

新版本示例工程支持的系列包括

  • STM32G0,STM32G4
  • STM32H7
  • STM32L0,STM32L1,STM32L4,STM32L5,STM32U5 (V4.0.1中包含)
  • STM32WB,STM32WL

其他STM32系列虽然没有提供直接的参考例程,但也可以参考示例代码的方式使用库文件,因为库是针对不同Cortex®-M内核提供的,并不区分产品系列。

代码质量进一步提升

V4版本加解密库的源码经过MISRAC:2012检查,加解密库的头文件也同样符合MISRAC:2012标准,对于有MISRAC合规需求的场景,V4将提供很好的支持。

更小代码+更高性能

V4的加解密库在优化方面做了很多提升。以STM32G4为例,我们可以用下表对比一下使用CryptoLib V3.1.3和V4.0.0版本,选择最高性能配置时的运算速度比较。可以看到,无论是对称算法,散列算法还是非对称算法,V4在性能上都有了很大提升,同时加解密库的代码量比V3还要更小。

“新版STM32加解密算法库——X-Cube-Cryptolib

更加灵活易用

方便灵活的方式选择加解密库的实现配置

V4的加解密库为每个内核提供一个单一的库文件,但是允许客户在其应用工程中可以根据速度和代码大小的需要选择不同的配置。这个配置在链接和使用过程中完成。

  • V3的加解密库在编译阶段使用不同配置,编译出不同的库文件
  • 而V4在相同的算法服务中实现了对不同配置(性能高低和代码量大小)的支持
  • 用户通过Construct API或者每个服务的Processing API来进行选择采用哪个实现
  • 缺省的配置以头文件形式提供

以ECDSA签名算法为例,使用签名函数之前,首先需要调用cmox_ecc_construct()函数,这个函数的第二个输入参数CMOX_ECC256_MATH_FUNCS就用来选择下层的具体实现使用哪一个。

“新版STM32加解密算法库——X-Cube-Cryptolib

CMOX_ECC256_MATH_FUNCS的定义决定了ECDSA的处理函数将会选择哪个实现,缺省配置为CMOX_MATH_FUNCS_SUPERFAST256,可选配置包括

  • CMOX_MATH_FUNCS_SMALL :代码量小,性能相对低
  • CMOX_MATH_FUNCS_FAST :性能高,代码量相对大
  • CMOX_MATH_FUNCS_SUPERFAST256:性能更高(针对长度为225到256的ECC曲线)

其他算法的配置也可以使用类似的方法进行性能和代码量大小的选择,具体请参考Middlewares\ST\STM32_Cryptographic\include\cmox_default_config.h

如果希望所有的配置都按照最小代码量来选择,则可以直接使用相同目录下的cmox_small_config.h头文件的定义,如果希望所有配置都按照最高性能来选择,则可以直接使用相同目录下的cmox_fast_config.h头文件的配置。

应用代码调用更加简洁

同样以ECDSA为例,使用V3版本加解密库,应用程序需要调用多个API才能完成 一个ECDSA Verification,而使用V4的加解密库只需要两个API即可完成。

V3

int32_t rv;
EC_stt EC_st;
membuf_stt Crypto_Buffer;
ECpoint_stt *PubKey = NULL;
ECDSAsignature_stt *sign = NULL;
uint8_t membuf[MAX_MEMBUF_SIZE];
ECDSAverifyCtx_stt verctx;

uint8_t pub_x[] = {…}, pub_y[] = {…};
uint8_t sign_r[] = {…}, sign_s[] = {…};
uint8_t digest[] = {…};

Crypto_Buf.pmBuf = membuf;
Crypto_Buf.mUsed = 0;
Crypto_Buf.mSize = sizeof(membuf);

/* Init the EC main struct */
rv = ECCinitEC(&EC_st, &Crypto_Buf);

/* Init the public key */
ECCinitPoint(&PubKey,
             &EC_st,
             &Crypto_Buf);
ECCsetPointCoordinate(PubKey,
               E_ECC_POINT_COORDINATE_X,
               pub_x,
               sizeof(pub_x));
ECCsetPointCoordinate(PubKey,
               E_ECC_POINT_COORDINATE_Y,
               pub_y,
               sizeof(pub_y));

/* Init the signature */
ECDSAinitSign(&sign,
              &EC_st,
              &Crypto_Buf);
ECDSAsetSignature(sign,
              E_ECDSA_SIGNATURE_R_VALUE,
              sign_r, sizeof(sign_r));
ECDSAsetSignature(sign,
              E_ECDSA_SIGNATURE_S_VALUE,
              sign_s, sizeof(sign_s));

/* Verification */
verif_ctx.pmEC = &EC_st;
verif_ctx.pmPubKey = PubKey;
rv = ECDSAverify(digest,
                 sizeof(digest),
                 sign,
                 &verif_ctx,
                 &Crypto_Buf);

V4

cmox_ecc_retval_t rv;
cmox_ecc_handle_t Ecc_Ctx;
uint8_t membuf[MAX_MEMBUF_SIZE];
uint32_t fault_check = CMOX_ECC_AUTH_FAIL;

uint8_t pubkey[] = {…}, digest[] = {…};
uint8_t signature[] = {…};

/* Construct a ECC context */
cmox_ecc_construct(&Ecc_Ctx,
        CMOX_ECC256_MATH_FUNCS,
        membuf, sizeof(membuf));

/* Verify directly the signature passing
   all the needed parameters */
rv = cmox_ecdsa_verify(&Ecc_Ctx,
        CMOX_ECC_CURVE_SECP256R1,
        pubkey, pubkey(Public_Key),
        digest, sizeof(digest),
        signature, sizeof(signature),
        &fault_check);

从V3到V4的快速切换

在V4的软件包中,还提供了一个wrapper实现,帮助以前V3的使用者快速切换到V4的,这个wrapper允许应用继续沿用V3 API但使用V4的库。当然,这种用法虽然快速切换到V4,但却不能最大化地利用V4的新优点,不是推荐用法,仅仅作为快速切换的目的使用。

“新版STM32加解密算法库——X-Cube-Cryptolib

算法认证

V4提供的加解密库经过了NIST CAVP(Cryptographic Algorithm Validation Program)的认证。

  • 认证测试覆盖了不同的性能和代码大小的配置方式(前面提到的可以通过头文件的宏定义进行的配置选择)
  • 认证基于Cortex®-M内核,而不是和某个特定的STM32系列绑定,所以可以适用于所有STM32系列

有关加解密库认证的详细信息可以参考此链接:资源链接

文档

所有Cryptolib V4相关的文档都通过STM32 MCU Wiki以网页形式提供,不再提供单独的UM和其他文档:https://wiki.st.com/stm32mcu/wiki/Category:Cryptographic_library

内容包括

● 加解密库简介、使用指南、密码学算法的基础知识

“新版STM32加解密算法库——X-Cube-Cryptolib

● 如何安全地使用加解密库、如何实现HKDF、加解密库认证信息、如何迁移到新版加解密库

“新版STM32加解密算法库——X-Cube-Cryptolib

● 加解密库的性能及资源占用信息

“新版STM32加解密算法库——X-Cube-Cryptolib

下载页面

V4版本加解密库可以从XCUBE-CRYPTOLIB常规的网址下载:

https://www.st.com/en/embedded-software/x-cube-cryptolib.html

V3版本加解密库可以通过以下链接下载:

https://www.st.com/en/embedded-software/x-cube-crypto-v3.html

来源:STM32
免责声明:本文为转载文章,转载此文目的在于传递更多信息,版权归原作者所有。本文所用视频、图片、文字如涉及作品版权问题,请联系小编进行处理(联系邮箱:cathy@eetrend.com)。

围观 568

很多初学的小伙伴认为STM32是从main函数开始执行,其实在main之前还有一个“启动”过程,下面分享一下在启动过程的那些内容。

基础

首先,你要知道STM32启动启动流程,你就需要掌握一点汇编基础知识。

汇编语言属于机器语言,或者说低级语言,C语言属于高级语言,所以,汇编和C语言在语法上差异很大。

如果你学底层开发,汇编的一些基础知识需要掌握。不需要精通,但需要看懂常见的汇编代码。

说明

STM32的启动文件与编译器有关,不同编译器,它的启动文件不同。

虽然启动文件(汇编)代码各有不同,但它们原理类似,都属于汇编程序。

我们拿基于Keil MDK的启动文件(.s)来举例,说一下要点内容。

分配堆栈

在基于MDK的启动文件开始,有一段汇编代码是分配堆栈大小的。

“STM32真的是从main开始执行的吗?"

这里重点知道堆栈数值大小就行。还有一段AREA(区域),表示分配一段堆栈数据段。

数值大小可以自己修改,也可以使用STM32CubeMX数值大小配置:

“STM32真的是从main开始执行的吗?"

在IAR中,是通过工程配置堆栈大小:

“STM32真的是从main开始执行的吗?"

向量表

相信大家都知道向量表,先看汇编代码:

“STM32真的是从main开始执行的吗?"

这个向量表就是对应手册中的那些内容:

“STM32真的是从main开始执行的吗?"

我们需要知道这个地方中的复位,程序上电之后,是跳到Reset_Handler这个位置。

执行代码

上面知道代码是从Reset_Handler开始执行,我们看Reset_Handler汇编代码:

“STM32真的是从main开始执行的吗?"

在启动的时候,执行了SystemInit这个函数。

之前标准外设库在SystemInit这个函数初始化了系统时钟,后面HAL库单独把那部分代码提出来了。

执行完SystemInit函数,就跳转到我们的main函数执行了。

来源:嵌入式专栏
免责声明:本文为转载文章,转载此文目的在于传递更多信息,版权归原作者所有。本文所用视频、图片、文字如涉及作品版权问题,请联系小编进行处理(联系邮箱:cathy@eetrend.com)。

围观 434

今天就再来分享一下关于Assert的内容。

1、写在前面

有经验的工程师都知道,随着软件版本的迭代,或者需求不断变更,我们的代码就会变得越来越“臃肿”。

在编码的过程中,如果没有注重一些细节,你的代码就可能存在许多隐藏的Bug。

那么,我们如何找出这些隐藏的Bug呢?

今天就说其中的一点:Assert断言。

2、关于Assert断言

什么是Assert断言?

编写代码时,我们总是会做出一些假设,断言就是用于在代码中捕捉这些假设,可以将断言看作是异常处理的一种高级形式。

断言表示为一些布尔表达式,程序员相信在程序中的某个特定点该表达式值为真。

可以在任何时候启用和禁用断言验证,因此可以在测试时启用断言,而在部署时禁用断言。

同样,程序投入运行后,最终用户在遇到问题时可以重新启用断言。

---来自百度百科

这里的概念,可能不好理解,简单举一个例子来说明吧。

有这么一个数组和函数:

int Array[5] = {0xA1, 0xB2, 0xC3, 0xD4, 0xE5};

int Fun(char i)
{
    return Array[i];
}

如果我们函数中不加Assert断言语句,你觉得直接调用会这个函数会有风险吗?

假如这么调用:

int a;

a = Fun(8);

很明显,就这么调用,会出错,且我们不容易发现错误在哪里。

但是,假如添加有Assert断言语句,错误就能一下找出来。

3、Assert断言实际应用

其实,Assert断言在很多标准的代码中,基本都有。我们还是拿STM32的代码来说明吧。

不管是STM32标准外设库、还是HAL、LL库源代码里面都有Assert断言机制。

不知道大家有没有注意过assert_param函数?

1)拿STM32最常见的GPIO初始化函数为例

A、标准外设库GPIO初始化:

“STM32函数库Assert断言机制"

B、HAL库GPIO初始化:

“STM32函数库Assert断言机制"

相信大家都看到过STM32库中的参数断言语句,他的作用就是用于检查函数传入参数是否正确。

2)STM32参数断言使能

STM32的assert_param参数断言函数是没有使能的,如下:

#define assert_param(expr) ((void)0)

也就是assert_param不起作用。

如果需要使用,就需要对其使能才行。

A、标准外设库

“STM32函数库Assert断言机制"

B、HAL库

道理一样,使能ASSERT,可以手动:

#define USE_FULL_ASSERT    1U

也可以通过STM32CubeMX配置:

“STM32函数库Assert断言机制"

3)代码大小

添加Assert断言之后,代码量肯定要增加,比如:

不使能assert_param代码量:

Code=5350 RO-data=360 RW-data=16 ZI-data=1152

使能assert_param:

Code=8300 RO-data=362 RW-data=16 ZI-data=1152

4)断言失败处理

断言失败,可根据实际项目需求,做出一定处理。比如:打印错误信息,存储错误日志等。

来源:嵌入式专栏
免责声明:本文为转载文章,转载此文目的在于传递更多信息,版权归原作者所有。本文所用视频、图片、文字如涉及作品版权问题,请联系小编进行处理(联系邮箱:
cathy@eetrend.com)。

围观 246

嵌入式初学者入门的第一个“项目”就是LED点灯,那么,本文带你看看51、STM32、Linux点灯有什么区别?

51点灯

51点灯,是很多单片机初学者的首选,难度也是相对比较低的。

准备工作:

  • 51开发板(以STC51单片机为例)

  • Keil C51、STC-ISP下载软件

51单片机开发,通常是直接操作寄存器,比如P1_0对应LED的IO口。

源代码:

#include <reg51.h>

sbit LED = P1^0;

void main()
{
    LED = 0;

    while(1);
}

STM32点灯

相对于51点灯,STM32点灯难度系数要大一点,因为STM32外设资源更多,启动文件更复杂,很多新手看到之后直接就放弃了。

其实,也很简单,下面分别通过寄存器和标准外设库点灯,你就知道明白了。

准备工作:

  • STM32开发板

  • Keil MDK、ST-LINK Utility下载软件

1.寄存器版本

直接操作寄存器,需要深入理解每个寄存器每个bit位的含义(不建议初学者一开始就学寄存器),而且,源码看起来比较多:

#include "stm32f4xx.h"

/* 主函数*/
int main(void)
{
    /*开启 GPIOH 时钟,使用外设时都要先开启它的时钟*/
    RCC_AHB1ENR |= (1<<7);

    /* LED 端口初始化 */
    /*GPIOH MODER10 清空*/
    GPIOH_MODER &= ~( 0x03<< (2*10));

    /*PH10 MODER10 = 01b 输出模式*/
    GPIOH_MODER |= (1<<2*10);

    /*GPIOH OTYPER10 清空*/
    GPIOH_OTYPER &= ~(1<<1*10);

    /*PH10 OTYPER10 = 0b 推挽模式*/
    GPIOH_OTYPER |= (0<<1*10);

    /*GPIOH OSPEEDR10 清空*/
    GPIOH_OSPEEDR &= ~(0x03<<2*10);

    /*PH10 OSPEEDR10 = 0b 速率 2MHz*/
    GPIOH_OSPEEDR |= (0<<2*10);

    /*GPIOH PUPDR10 清空*/
    GPIOH_PUPDR &= ~(0x03<<2*10);

    /*PH10 PUPDR10 = 01b 上拉模式*/
    GPIOH_PUPDR |= (1<<2*10);

    /*PH10 BSRR 寄存器的 BR10 置 1,使引脚输出低电平*/
    GPIOH_BSRR |= (1<<16<<10);  //点灯

    while (1);
}

.标准外设库版本

标准外设库,就是ST官方已经把寄存器进行封装过一次,你直接调用函数借口即可。

#include "stm32f10x.h"

/*  LED时钟端口、引脚定义*/
#define LED_PORT       GPIOC   
#define LED_PIN       GPIO_Pin_0
#define LED_PORT_RCC            RCC_APB2Periph_GPIOC

void LED_Init()
{
    GPIO_InitTypeDef GPIO_InitStructure;        //定义结构体变量

    RCC_APB2PeriphClockCmd(LED_PORT_RCC, ENABLE);

    GPIO_InitStructure.GPIO_Pin = LED_PIN;                //选择你要设置的IO口
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;      //设置推挽输出模式
    GPIO_InitStructure.GPIO_Speed=GPIO_Speed_50MHz;       //设置传输速率
    GPIO_Init(LED_PORT,&GPIO_InitStructure);              //初始化GPIO 

    GPIO_SetBits(LED_PORT, LED_PIN);                       //将LED端口拉高,熄灭LED
}

int main()
{  
  LED_Init();
  GPIO_ResetBits(LED_PORT,GPIO_Pin_0);//点灯

    while(1);
}

Linux点灯

Linux点灯,相对来说就更复杂了。当然,有一些已经搭建好的环境,就相对简单一点,也比较容易。如果自己一步一步移植系统、写驱动···就很复杂。

1.树莓派

我们这里以【开源库wiringPi】为例:

1、下载U-boot源码,配置、编译;

2、下载Linux内核、配置、编译(一般开发板都会有现成的配置文件);

3、制作跟文件系统;(以上三个步骤,如果没有一定的Linux基础,可以使用一键烧写)

4、移植开源库WiringPi;

5、查看电路图找到LED对应的引脚,程序需要用到引脚号;

6、编码、交叉编译;

7、下载运行。

准备工作做好之后,点灯的源码就比较简单:

#include <wiringPi.h>

int main(void)
{
    wiringPiSetup() ;
    pinMode (7, OUTPUT);
    gitalWrite(7, HIGH);
    while(1);
}

2.Linux驱动点灯

在所有的点灯方法中,这个方法难度系数极高,涵盖了嵌入式开发从上层应用到底层驱动。步骤涉及了驱动代码编写、Linux内核模块添加、移植操作系统、Linux应用程序编写。

这里分享一下mini2440经典LED驱动源码:

#include <linux/init.h>
#include <linux/module.h>
#include <linux/fs.h>
#include <linux/miscdevice.h>
#include <linux/ioctl.h>
#include <linux/gpio.h> 
#include <mach/regs-gpio.h> 
#include "led.h" 

static int led_open(struct inode *inode, struct file *file)
{  
    s3c2410_gpio_cfgpin(S3C2410_GPB(5), S3C2410_GPIO_OUTPUT);
    s3c2410_gpio_setpin(S3C2410_GPB(5), 1);   
    return 0;
} 

static int led_ioctl(struct inode *inode, struct file *file, unsigned int cmd, unsigned long arg)
{  
    switch (cmd) {  
        case LED_ON:    
            s3c2410_gpio_setpin(S3C2410_GPB(5), 0);    
            return 0;  
        case LED_OFF:    
            s3c2410_gpio_setpin(S3C2410_GPB(5), 1);    
            return 0;  
        default:    
            return -EINVAL;  
        }
} 

static struct file_operations led_fops = {  
    .owner = THIS_MODULE,  
    .open = led_open,  
    .ioctl = led_ioctl,
}; 

static struct miscdevice led_misc = {  
    .minor = MISC_DYNAMIC_MINOR,  
    .name = "led",  
    .fops = &led_fops,
}; 

static int led_init(void){  
    return misc_register(&led_misc);
} 

static void led_exit(void){  
    misc_deregister(&led_misc);
} 

MODULE_LICENSE("Dual BSD/GPL");
module_init(led_init);
module_exit(led_exit);

驱动写了,然后就是应用层代码:

#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <sys/ioctl.h>
#include <unistd.h>
#include <stdio.h>
#include "led.h" 

int main(void){        
    int fd;         
    fd = open("/dev/led", O_RDWR);         
    if (fd < 0) {                
        printf("No such device!\n");                
        return -1;        
    }         
    while (1) {                
        ioctl(fd, LED_ON);                
        sleep(1);                
        ioctl(fd, LED_OFF);                
        sleep(1);        
        }         

    close(fd);         
    return 0;
}

最后

点灯是基础,如果你从事嵌入式开发,我觉得这些点灯是最基础的第一步。

可能第一步很难,但走过第一步,相信下一步就会变得更容易。

来源:嵌入式专栏
免责声明:本文为转载文章,转载此文目的在于传递更多信息,版权归原作者所有。本文所用视频、图片、文字如涉及作品版权问题,请联系小编进行处理(联系邮箱:cathy@eetrend.com)。

围观 135

SPWM(Sinusoidal PWM)法是一种比较成熟的,目前使用较广泛的PWM法。SPWM法就是以该结论为理论基础,用脉冲宽度按正弦规律变化而和正弦波等效的PWM波形即SPWM波形控制逆变电路中开关器件的通断,使其输出的脉冲电压的面积与所希望输出的正弦波在相应区间内的面积相等,通过改变调制波的频率和幅值则可调节逆变电路输出电压的频率和幅值。本文主要详解stm32产生spwm原理及程序,首先来了解一下生成SPWM波的基理是什么,具体得跟随小编一起来了解一下。

生成SPWM波的基理

由于正弦交流量是典型的模拟量,传统发电机难以完成高频交流电流输出,而功率半导体器件于模拟状态工作时产生的动态损耗剧增,于是,用开关量取代模拟量成为必由之路,并归结为脉冲电路的运行过程,从而构成了运动控制系统中的功率变换器或电源引擎。典型的H桥逆变电路很容易理解(图1a)

“一文解析STM32产生spwm原理及程序"

对角联动的两个开关器件和与之对应的另一组对角桥臂同时实施交替的开关作业时,建立运行后,流经负载的电流即为交流电流(图1b),考虑到功率器件关断时的滞后特性避免造成短路,通常都做成(图1c)的波形结构。显然开关器件输出的是方波(矩形波)交流电流。
  
在交流应用场合,多数负载要求输入的是正弦波电流。
  
电工学认为,周期性的非正弦交流量是直流、正弦波和余弦波等分量的集合,或者是非正弦波也可以分解为相位差和频率不同的正弦波以及直流分量。
  
不良波形或失真严重的正弦交流量必然产生大量的低次、高次及分数谐波,丰富的谐波分量与基波叠加的情景使得正负峰值几乎同时发生,换向突变时急剧的运动状态将对负载造成冲击并导致负载特性的不稳定或漂移,又加重了滤波器件的负担,损耗也随之增大,非但降低了电网的功率因数,还对周边设备造成不良影响。
  
在高频化和大功率电力变换场合,装置内部急剧的电流变化,不但使器件承受很大电磁应力,并向装置周围空间辐射有害电磁波污染环境,这种电磁干扰(Electro Magnetic Interference简称EMI)还会引发周围设备的误动作及造成电能计量紊乱。抑制谐波和EMI的防御仍为重要课题或技术指标。
  
可见,简单的方波在功率应用场合下显示出了不尽如人意的一面。当然,在不触及负载特性、能量转换效率、环境污染和系统综合技术指标以及小功率应用场合的前提下,就控制方法而言则显得容易些。
  
自然采样法是一种基于面积等效理念的能量转换形式,其原理极为简单而且直观,并具备十分确切的数理依据,通用性及可操作性也很强。当正弦基波与若千个等幅的三角载波在时间轴上相遇时,并令正弦波的零点与三角波的峰点处于同相位(图2a),所得的交点(p)表达为时间意义上的相位角和对应的瞬时幅值,交点间的相位区间段表示以正弦部分为有效输出的矩形脉冲群(图2b)。
  

“一文解析STM32产生SPWM原理及程序"

由此,SPWM波的基本概念是每一周期的基波与若千个载波进行调制(载波的数量与基波之比即为载波比),并依次按正弦函数值定位的有效相位区间集合成等幅不等宽且总面积等效于正弦量平均值的正弦化脉冲序列。对应于正弦量的正负半周,实施双路调制或单路分相处理及放大后,控制驱动功率开关器件运行,最终得正弦化交流量的样本波形如(图3)所示,滤波后流经负载的电流即为正弦波电流。
  

“一文解析STM32产生SPWM原理及程序"

stm32产生spwm原理及程序

SPWM波的形成原理

利用正弦波的各点幅值成正弦变换的思想,我们可以类似的采取在一系列方波中,让占空比中高度不变,占空比大小呈正弦变换的这样的一种做法,这样占空比大小呈正弦变换的波我们称之为SPWM波。网上有生成正弦波采样点数组的软件,可以选择采样点数和精度。本次实验中就需要用这个软件来产生我们需要的正弦表。

STM32产生SPWM程序

“一文解析STM32产生SPWM原理及程序"

“一文解析STM32产生SPWM原理及程序"

“一文解析STM32产生SPWM原理及程序"

“一文解析STM32产生SPWM原理及程序"

来源:网络
免责声明:本文为转载文章,转载此文目的在于传递更多信息,版权归原作者所有。本文所用视频、图片、文字如涉及作品版权问题,请联系小编进行处理(联系邮箱:
cathy@eetrend.com)。

围观 874

GPIO是通用输入/输出端口的简称,是STM32可控制的引脚。GPIO的引脚与外部硬件设备连接,可实现与外部通讯、控制外部硬件或者采集外部硬件数据的功能。

STM32F103ZET6芯片为144脚芯片,包括7个通用目的的输入/输出口(GPIO)组,分别为GPIOA、GPIOB、GPIOC、GPIOD、GPIOE、GPIOF、GPIOG,同时每组GPIO口组有16个GPIO口。通常简略称为PAx、PBx、PCx、PDx、PEx、PFx、PGx,其中x为0-15。

STM32的大部分引脚除了当GPIO使用之外,还可以复用为外设功能引脚,比如串口。

GPIO基本结构

每个GPIO内部都有这样的一个电路结构,这个结构在本文下面会具体介绍。

“STM32的GPIO电路原理"

保护二极管:IO引脚上下两边两个二极管用于防止引脚外部过高、过低的电压输入。当引脚电压高于VDD时,上方的二极管导通;当引脚电压低于VSS时,下方的二极管导通,防止不正常电压引入芯片导致芯片烧毁。但是尽管如此,还是不能直接外接大功率器件,须加大功率及隔离电路驱动,防止烧坏芯片或者外接器件无法正常工作。

P-MOS管和N-MOS管:由P-MOS管和N-MOS管组成的单元电路使得GPIO具有“推挽输出”和“开漏输出”的模式。这里的电路会在下面很详细地分析到。

TTL肖特基触发器:信号经过触发器后,模拟信号转化为0和1的数字信号。但是,当GPIO引脚作为ADC采集电压的输入通道时,用其“模拟输入”功能,此时信号不再经过触发器进行TTL电平转换。ADC外设要采集到的原始的模拟信号。

这里需要注意的是,在查看《STM32中文参考手册V10》中的GPIO的表格时,会看到有“FT”一列,这代表着这个GPIO口时兼容3.3V和5V的。如果没有标注“FT”,就代表着不兼容5V。
STM32的GPIO工作方式

GPIO支持的输入输出模式:

  • GPIO_Mode_AIN 模拟输入

  • GPIO_Mode_IN_FLOATING 浮空输入

  • GPIO_Mode_IPD 下拉输入

  • GPIO_Mode_IPU 上拉输入

  • GPIO_Mode_Out_OD 开漏输出

  • GPIO_Mode_Out_PP 推挽输出

  • GPIO_Mode_AF_OD 复用开漏输出

  • GPIO_Mode_AF_PP 复用推挽输出

每个I/O口可以自由编程,但I/O口寄存器必须按32位字被访问。

下面将具体介绍GPIO的这八种工作方式:

浮空输入模式

“STM32的GPIO电路原理"

浮空输入模式下,I/O端口的电平信号直接进入输入数据寄存器。也就是说,I/O的电平状态是不确定的,完全由外部输入决定;如果在该引脚悬空(在无信号输入)的情况下,读取该端口的电平是不确定的。

上拉输入模式

“STM32的GPIO电路原理"

上拉输入模式下,I/O端口的电平信号直接进入输入数据寄存器。但是在I/O端口悬空(在无信号输入)的情况下,输入端的电平可以保持在高电平;并且在I/O端口输入为低电平的时候,输入端的电平也还是低电平。

下拉输入模式

“STM32的GPIO电路原理"

下拉输入模式下,I/O端口的电平信号直接进入输入数据寄存器。但是在I/O端口悬空(在无信号输入)的情况下,输入端的电平可以保持在低电平;并且在I/O端口输入为高电平的时候,输入端的电平也还是高电平。

模拟输入模式

“STM32的GPIO电路原理"

模拟输入模式下,I/O端口的模拟信号(电压信号,而非电平信号)直接模拟输入到片上外设模块,比如ADC模块等等。

开漏输出模式

“STM32的GPIO电路原理"

开漏输出模式下,通过设置位设置/清除寄存器或者输出数据寄存器的值,途经N-MOS管,最终输出到I/O端口。这里要注意N-MOS管,当设置输出的值为高电平的时候,N-MOS管处于关闭状态,此时I/O端口的电平就不会由输出的高低电平决定,而是由I/O端口外部的上拉或者下拉决定;当设置输出的值为低电平的时候,N-MOS管处于开启状态,此时I/O端口的电平就是低电平。同时,I/O端口的电平也可以通过输入电路进行读取;注意,I/O端口的电平不一定是输出的电平。

开漏复用输出模式

“STM32的GPIO电路原理"

开漏复用输出模式,与开漏输出模式很是类似。只是输出的高低电平的来源,不是让CPU直接写输出数据寄存器,取而代之利用片上外设模块的复用功能输出来决定的。

推挽输出模式

“STM32的GPIO电路原理"

推挽输出模式下,通过设置位设置/清除寄存器或者输出数据寄存器的值,途经P-MOS管和N-MOS管,最终输出到I/O端口。这里要注意P-MOS管和N-MOS管,当设置输出的值为高电平的时候,P-MOS管处于开启状态,N-MOS管处于关闭状态,此时I/O端口的电平就由P-MOS管决定:高电平;当设置输出的值为低电平的时候,P-MOS管处于关闭状态,N-MOS管处于开启状态,此时I/O端口的电平就由N-MOS管决定:低电平。同时,I/O端口的电平也可以通过输入电路进行读取;注意,此时I/O端口的电平一定是输出的电平。

推挽复用输出模式

“STM32的GPIO电路原理"

推挽复用输出模式,与推挽输出模式很是类似。只是输出的高低电平的来源,不是让CPU直接写输出数据寄存器,取而代之利用片上外设模块的复用功能输出来决定的。

总结与分析

什么是推挽结构和推挽电路?

推挽结构一般是指两个参数相同的三极管或MOS管分别受两互补信号的控制,总是在一个三极管或MOS管导通的时候另一个截止。高低电平由输出电平决定。

推挽电路是两个参数相同的三极管或MOSFET,以推挽方式存在于电路中,各负责正负半周的波形放大任务。电路工作时,两只对称的功率开关管每次只有一个导通,所以导通损耗小、效率高。输出既可以向负载灌电流,也可以从负载抽取电流。推拉式输出级既提高电路的负载能力,又提高开关速度。
开漏输出和推挽输出的区别?

开漏输出:只可以输出强低电平,高电平得靠外部电阻拉高。输出端相当于三极管的集电极。适合于做电流型的驱动,其吸收电流的能力相对强(一般20ma以内)。

推挽输出:可以输出强高、低电平,连接数字器件。

关于推挽输出和开漏输出,最后用一幅最简单的图形来概括:

“STM32的GPIO电路原理"

该图中左边的便是推挽输出模式,其中比较器输出高电平时下面的PNP三极管截止,而上面NPN三极管导通,输出电平VS+;当比较器输出低电平时则恰恰相反,PNP三极管导通,输出和地相连,为低电平。右边的则可以理解为开漏输出形式,需要接上拉。

在STM32中选用怎样选择I/O模式?

  • 浮空输入_IN_FLOATING ——浮空输入,可以做KEY识别,RX1

  • 带上拉输入_IPU——IO内部上拉电阻输入

  • 带下拉输入_IPD—— IO内部下拉电阻输入

  • 模拟输入_AIN ——应用ADC模拟输入,或者低功耗下省电

  • 开漏输出_OUT_OD ——IO输出0接GND,IO输出1,悬空,需要外接上拉电阻,才能实现输出高电平。当输出为1时,IO口的状态由上拉电阻拉高电平,但由于是开漏输出模式,这样IO口也就可以由外部电路改变为低电平或不变。可以读IO输入电平变化,实现C51的IO双向功能

  • 推挽输出_OUT_PP ——IO输出0-接GND, IO输出1 -接VCC,读输入值是未知的

  • 复用功能的推挽输出_AF_PP ——片内外设功能(I2C的SCL、SDA)

  • 复用功能的开漏输出_AF_OD——片内外设功能(TX1、MOSI、MISO.SCK.SS)

来源:STM32嵌入式开发
免责声明:本文为转载文章,转载此文目的在于传递更多信息,版权归原作者所有。本文所用视频、图片、文字如涉及作品版权问题,请联系小编进行处理(联系邮箱:
cathy@eetrend.com)。

围观 130

新建工程文件夹

建立名字为LED的文件夹存放工程文件,其中再建立两个文件夹,Listing文件夹用于存放编译器编译时候产生的C语言、汇编、链接文件,Output文件夹用于存放编译产生的调试信息、hex文件、预览信息、封装库等。

文件夹建好之后,在LED文件夹下存放startup_stm32f10x_hd.s、stm32f10x.h、main.c文件。前两个文件可以在STM32F1xx的固件库中找到,第三个文件是空文件。

在Keil5中新建工程的步骤

如下图所示,Project-New,新建工程,工程名为Led,点击保存。

“Keil5软件配置与新建STM32工程的步骤"

点击保存之后,弹出如下窗口,选择芯片型号。根据你开发板使用的芯片具体的型号来选择。如果这里没有出现你想要的CPU型号,或者一个型号都没有,那么肯定是你的KEIL5没有添加Device库,关于如何添加请往下看。

“Keil5软件配置与新建STM32工程的步骤"

安装Device库

下载KEIL MDK5以后是没有安装device的,如果此时创建工程会找不到目标芯片,如下图所示:

“Keil5软件配置与新建STM32工程的步骤"

此时我们就要安装自己需要的芯片系列,比如STM32F1系列。首先选择Project-Manage-Pack Installer,此时出现下面如下界面:

“Keil5软件配置与新建STM32工程的步骤"

选择菜单栏中的Packs,点击Check for Updates,此时就会出现最新的支持的CPU系列,更新完毕之后会出现如下界面:

“Keil5软件配置与新建STM32工程的步骤"

我们选择需要安装的芯片厂商,这里因为要安装STM32F1系列,所以选择ST公司,然后在右侧出现了STM系列的芯片,如上图右侧箭头所示,此时点击需要安装的STM32系列,这里我需要安装的是STM32F1系列,点击安装,此时软件会下载对应的芯片包,如下图所示:

“Keil5软件配置与新建STM32工程的步骤"

这个下载过程比较慢,耐心等待,安装完毕之后,关闭KEIL5,重新打开KEIL5,此时新建工程,就出现了需要的芯片。

用寄存器控制 STM32 时我们不需要在线添加库文件,如关掉下图窗口。

“Keil5软件配置与新建STM32工程的步骤"

向工程中添加文件

在新建的工程中添加文件,文件从本地建好的工程文件夹下获取,双击组文件夹就会出现添加文件的路径,然后选择文件即可,如下图所示。

“Keil5软件配置与新建STM32工程的步骤"

Keil5软件配置

配置魔术棒

如下图所示,Target中选中微库“Use MicroLib”,为了编写串口驱动时可以使用printf函数。

“Keil5软件配置与新建STM32工程的步骤"

Output 选项卡中把输出文件夹定位到我们工程目录下的 output 文件夹,如果想在编译的过程中生成 hex 文件,那么那 Create HEX File 选项勾上。

“Keil5软件配置与新建STM32工程的步骤"

点击Listing选项卡中的Select Folder for Listings,把输出文件夹定位到先前创建的Listings文件夹。

“Keil5软件配置与新建STM32工程的步骤"

配置下载器

在仿真器连接好电脑和开发板且开发板供电正常的情况下,打开KEIL5软件,在魔术棒选项卡里面选择所用仿真器的型号,如下图所示。

“Keil5软件配置与新建STM32工程的步骤"

在Utilities中勾选Use Debug Driver,如下图所示。

“Keil5软件配置与新建STM32工程的步骤"

点击Debug中的Settings,选择相应仿真器,勾选SW,Clock选为5MHz,Reset选择Autodetect。

“Keil5软件配置与新建STM32工程的步骤"

在Flash Download中做如下图所示的配置,勾选Reset and run,程序下载后自动运行,不用先手动复位。

“Keil5软件配置与新建STM32工程的步骤"

Keil5下载程序

如上,在Keil5中新建了工程,并对软件进行了正确配置之后,就可以点击下图1处的Rebuild按钮编译,再点击2处的LOAD下载到开发板上运行。

“Keil5软件配置与新建STM32工程的步骤"

来源:STM32嵌入式开发
免责声明:本文为转载文章,转载此文目的在于传递更多信息,版权归原作者所有。本文所用视频、图片、文字如涉及作品版权问题,请联系小编进行处理(联系邮箱:cathy@eetrend.com)。

围观 890

页面

订阅 RSS - STM32