[GD32L233C-START 评测] 二、 测评从点灯开始

wo4fisher   2022-1-16 14:50 楼主

入门一款单片机,一般从单片机输出0/1开始,最直观的现象现象就是点亮一个LED、让一个LED亮灭闪烁、多个LED流水灯等

GD32L233C-START板载4颗LED,因此,就着这4颗LED,也是可以有很多玩法的。

一、已有资源分析

  官方提供了丰富的资源,主要有GD32L23x_Firmware_Library_V1.0.1,GD32L23x_AddOn_V1.0.0(GigaDevice.GD32L23x_DFP_1.0.0.pack)和GD32L23x_Demo_Suites_V1.1.0。

  通过分析以上资源的源码,GD32L23x_Firmware_Library_V1.0.1是最新的标准库版本,基于V1.0.0,部分外设有所修改。同时提供了基于GD32L233R-EVAL-V1.0 board的丰富例程。

  GD32L23x_AddOn_V1.0.0提供了KEIL和IAR的pack包。安装后KEIL中显示版本是V0.0.0,但通过打开库文件源码,可以看到应该和GD32L23x_Firmware_Library_V1.0.1是同步的。

  GD32L23x_Demo_Suites_V1.1.0主要提供了GD32L233C-START、GD32L233K_START\GD32L233R_EVAL三块板子的例程。因为START作为入门板子的原因,板载资源有限,例程仅有LED、Key、EXTI_Key、USART、TIMER_Key、USBD_CDC的例程。

  另外三个资源包虽然标准库版本一样,但是查看文件大小,部分源代码文件大小有差异。这个需要在使用的时候注意一下。

二、 GD32L233C-START  LED硬件电路

image.png   GD32L233C-START的LED总共有4个,分别有PA7、PA8、PC6、PC7四个引脚控制,高电平有效。

三、GD32L23x_Demo_Suites_V1.1.0 中的点灯程序

  将GD32L23x_Demo_Suites_V1.1.0 压缩包解压到非中文目录,然后打开第一个例程,编译,0error,0warning。然后确认一下工程的option选项信息,使用CMSIS-DAP。

  下载后,可以看到4颗LED,依次点亮。

四、源码分析

    4.1 systick配置及使用

        4.1.1 配置

void systick_config(void)
{
    /* setup systick timer for 1000Hz interrupts */
    if(SysTick_Config(SystemCoreClock / 1000U)) {
        /* capture error */
        while(1) {
        }
    }
    /* configure the systick handler priority */
    NVIC_SetPriority(SysTick_IRQn, 0x00U);
}

  配置程序比较简单,调用两个库函数,SysTick_Config()根据系统时钟和定时周期来进行systick的时钟配置和工作模式的配置。SysTick_Config()配置systick的中断优先级。

        4.1.2 使用

volatile static uint32_t delay;
void delay_decrement(void)
{
    if(0U != delay) {
        delay--;
    }
}
void delay_1ms(uint32_t count)
{
    delay = count;

    while(0U != delay) {
    }
}

  首先,定义一个用于tick中断中进行减操作的变量。然后delay_decrement()函数在tick中断中被调用,当delay不为0,减一。使用delay_1ms()在需要ms级延时的地方进行延时,参数为要延时的毫秒数。

  ***这样的延时函数,其实是有局限性的。比如在调用一次delay_1ms(10)之后,经过10ms延时,在下一次调用delay_1ms()之前,delay是一直为0的。相较于STM32中一直使用的systick的延时方式,GD给的tick延时函数有非常大的局限性。也就只能作为延时函数使用了。

4.2 GPIO配置及置位/清零操作

    /* enable the LED GPIO clock */
    rcu_periph_clock_enable(RCU_GPIOA);
    /* configure LED GPIO pin */
    gpio_mode_set(GPIOA, GPIO_MODE_OUTPUT, GPIO_PUPD_NONE, GPIO_PIN_7 | GPIO_PIN_8);
    gpio_output_options_set(GPIOA, GPIO_OTYPE_PP, GPIO_OSPEED_50MHZ, GPIO_PIN_7 | GPIO_PIN_8);
    /* reset LED GPIO pin */
    gpio_bit_reset(GPIOA, GPIO_PIN_7 | GPIO_PIN_8);
    /* set LED GPIO pin */
    gpio_bit_set(GPIOA, GPIO_PIN_7 | GPIO_PIN_8);

  三部曲:第一步:开时钟;第二步:gpio_mode_set()设置输入输出、上下拉,gpio_output_options_set()设置输出类型、速度;第三步:gpio_bit_reset()、gpio_bit_set()函数进行引脚输出置位/清零操作。  每一个函数,操作的引脚都可以其中任意多个,并且可以是非连续引脚。

/* set GPIO pin bit */
void gpio_bit_set(uint32_t gpio_periph, uint32_t pin);
/* reset GPIO pin bit */
void gpio_bit_reset(uint32_t gpio_periph, uint32_t pin);
/* write data to the specified GPIO pin */
void gpio_bit_write(uint32_t gpio_periph, uint32_t pin, bit_status bit_value);
/* write data to the specified GPIO port */
void gpio_port_write(uint32_t gpio_periph, uint16_t data);

/* get GPIO pin input status */
FlagStatus gpio_input_bit_get(uint32_t gpio_periph, uint32_t pin);
/* get GPIO port input status */
uint16_t gpio_input_port_get(uint32_t gpio_periph);
/* get GPIO pin output status */
FlagStatus gpio_output_bit_get(uint32_t gpio_periph, uint32_t pin);
/* get GPIO port output status */
uint16_t gpio_output_port_get(uint32_t gpio_periph);

/* set GPIO alternate function */
void gpio_af_set(uint32_t gpio_periph, uint32_t alt_func_num, uint32_t pin);
/* lock GPIO pin bit */
void gpio_pin_lock(uint32_t gpio_periph, uint32_t pin);

/* toggle GPIO pin status */
void gpio_bit_toggle(uint32_t gpio_periph, uint32_t pin);
/* toggle GPIO port status */
void gpio_port_toggle(uint32_t gpio_periph);

  库文件中,对于GPIO的操作,无论是输入还是输出,基本上涵盖了日常用到的所有操作。使用的时候直接调用对应的函数就行。

流水灯改造:

  将下边的代码做以下修改

    /* reset LED GPIO pin   修改前*/
    gpio_bit_reset(GPIOA, GPIO_PIN_7 | GPIO_PIN_8);
    gpio_bit_reset(GPIOC, GPIO_PIN_6 | GPIO_PIN_7);

    /* reset LED GPIO pin   修改后*/
    gpio_bit_reset(GPIOA, GPIO_PIN_7 | GPIO_PIN_8);
    gpio_bit_set(GPIOC, GPIO_PIN_6 | GPIO_PIN_7);

  然后将while(1)中的内容做如下改动(将原来的代码注释掉,增加下边的三行):

        
          /* turn on LED1, turn off LED4 */
//        gpio_bit_set(GPIOA, GPIO_PIN_7);
//        gpio_bit_reset(GPIOC, GPIO_PIN_7);
//        delay_1ms(500);

//        /* turn on LED2, turn off LED1 */
//        gpio_bit_set(GPIOA, GPIO_PIN_8);
//        gpio_bit_reset(GPIOA, GPIO_PIN_7);
//        delay_1ms(500);

//        /* turn on LED3, turn off LED2 */
//        gpio_bit_set(GPIOC, GPIO_PIN_6);
//        gpio_bit_reset(GPIOA, GPIO_PIN_8);
//        delay_1ms(500);

//        /* turn on LED4, turn off LED3 */
//        gpio_bit_set(GPIOC, GPIO_PIN_7);
//        gpio_bit_reset(GPIOC, GPIO_PIN_6);
//        delay_1ms(500);
			    
		  gpio_bit_toggle(GPIOA, GPIO_PIN_7 | GPIO_PIN_8);
		  gpio_bit_toggle(GPIOC, GPIO_PIN_6 | GPIO_PIN_7);
		  delay_1ms(500);

  一个新的流水灯就有了。有了标准库,点灯是不是很简单。

本帖最后由 wo4fisher 于 2022-1-16 14:52 编辑
水不撩不知深浅 人不拼怎知输赢

回复评论 (5)

有了标准库,点灯确实很简单。

点赞  2022-1-16 21:09

可惜我没有抽到,没有机会测玩了,有一段时间没有玩单片机了.

点赞  2022-1-17 08:52
引用: Jacktang 发表于 2022-1-16 21:09 有了标准库,点灯确实很简单。

    其实,主要还是底层决定的。arm框架下,用了一款芯片,很容易迁移到别的厂家同样内核的芯片上。

    ST在手册和标准库(当然不只是标准库)以及芯片配置代码(cubemx)自动化上,国产大厂好像追的不是很给力,反而一些小厂做的还好一些。

水不撩不知深浅 人不拼怎知输赢
点赞  2022-1-17 20:21

ST家族

默认摸鱼,再摸鱼。2022、9、28
点赞  2022-1-17 21:03

会用C语言,有了标准库,点灯确实很简单。

点赞  2022-1-18 13:52
电子工程世界版权所有 京B2-20211791 京ICP备10001474号-1 京公网安备 11010802033920号
    写回复