Sfoglia il codice sorgente

增加iwgd/led/sd sample

misonyo 7 anni fa
parent
commit
3cdfa0cadd
3 ha cambiato i file con 277 aggiunte e 0 eliminazioni
  1. 74 0
      iwdg_sample.c
  2. 76 0
      led_blink_sample.c
  3. 127 0
      sd_sample.c

+ 74 - 0
iwdg_sample.c

@@ -0,0 +1,74 @@
+/*
+ * Copyright (c) 2006-2018, RT-Thread Development Team
+ *
+ * SPDX-License-Identifier: Apache-2.0
+ *
+ * Change Logs:
+ * Date           Author       Notes
+ * 2018-09-25     misonyo      first edition.
+ */
+/* 
+ * 程序清单:这是一个独立看门狗设备使用例程
+ * 例程导出了 iwdg_sample 命令到控制终端
+ * 命令调用格式:iwdg_sample iwg
+ * 命令解释:命令第二个参数是要使用的看门狗设备名称,为空则使用例程默认的看门狗设备
+ * 程序功能:程序通过设备名称查找看门狗设备,然后初始化设备并设置看门狗设备溢出时间。
+ *           然后设置空闲线程回调函数,在回调函数里会喂狗。
+*/
+
+#include <rtthread.h>
+#include <rtdevice.h>
+
+#define IWDG_DEVICE_NAME    "iwg"
+
+static rt_device_t wdg_dev;
+
+static void idle_hook(void)
+{
+    /* 在空闲线程的回调函数里喂狗 */
+    rt_device_control(wdg_dev, RT_DEVICE_CTRL_WDT_KEEPALIVE, NULL);
+}
+
+static int iwdg_sample(int argc,char *argv[])
+{
+    rt_err_t result = RT_EOK;
+    rt_uint32_t timeout = 1000;    /* 超时时间为1000ms*/
+    char device_name[RT_NAME_MAX];
+
+    /* 判断命令行参数是否给定了设备名称 */
+    if (argc == 2)
+    {
+        rt_strncpy(device_name, argv[1], RT_NAME_MAX);
+    }
+    else
+    {
+        rt_strncpy(device_name, IWDG_DEVICE_NAME, RT_NAME_MAX);
+    }
+    /* 根据设备名称查找看门狗设备,获取设备句柄 */
+    wdg_dev = rt_device_find(device_name);
+    if (!wdg_dev)
+    {
+        rt_kprintf("find %s failed!\n",device_name);
+        return RT_ERROR;
+    }
+    /* 初始化设备 */
+    result = rt_device_init(wdg_dev);
+    if (result != RT_EOK)
+    {
+        rt_kprintf("initialize %s failed!\n",device_name);
+        return RT_ERROR;
+    }
+    /* 设置看门狗溢出时间 */
+    result = rt_device_control(wdg_dev, RT_DEVICE_CTRL_WDT_SET_TIMEOUT, (void*)timeout);
+    if (result != RT_EOK)
+    {
+        rt_kprintf("set %s timeout failed!\n",device_name);
+        return RT_ERROR;
+    }
+    /* 设置空闲线程回调函数 */
+    rt_thread_idle_sethook(idle_hook);
+
+    return result;
+}
+/* 导出到 msh 命令列表中 */
+MSH_CMD_EXPORT(iwdg_sample, iwdg sample);

+ 76 - 0
led_blink_sample.c

@@ -0,0 +1,76 @@
+/*
+ * Copyright (c) 2006-2018, RT-Thread Development Team
+ *
+ * SPDX-License-Identifier: Apache-2.0
+ *
+ * Change Logs:
+ * Date           Author       Notes
+ * 2018-09-25     misonyo      first edition.
+ */
+/* 
+ * 程序清单:这是一个通过PIN脚控制LED亮灭的使用例程
+ * 例程导出了 led_sample 命令到控制终端
+ * 命令调用格式:led_sample 41
+ * 命令解释:命令第二个参数是要使用的PIN脚编号,为空则使用例程默认的引脚编号。
+ * 程序功能:程序创建一个led线程,线程每隔1000ms改变PIN脚状态,达到控制led灯
+ *            亮灭的效果。
+*/
+
+#include <rtthread.h>
+#include <rtdevice.h>
+#include <stdlib.h>
+
+/* PIN脚编号,查看驱动文件drv_gpio.c确定 */
+#define LED_PIN_NUM    41
+static int pin_num;
+
+static void led_entry(void *parameter)
+{
+    int count = 0;
+    /* 设置PIN脚模式为输出 */
+    rt_pin_mode(pin_num, PIN_MODE_OUTPUT);
+
+    while (1)
+    {
+        count++;
+        rt_kprintf("thread run count : %d\r\n", count);
+        /* 拉低PIN脚 */
+        rt_pin_write(pin_num, PIN_LOW);
+        rt_kprintf("led on!\r\n");
+        /* 延时1000ms */
+        rt_thread_mdelay(1000);
+
+        /* 拉高PIN脚 */
+        rt_pin_write(pin_num, PIN_HIGH);
+        rt_kprintf("led off!\r\n");
+        rt_thread_mdelay(1000);
+    }
+}
+
+static void led_sample(int argc,char *argv[])
+{
+    rt_thread_t tid;
+
+    /* 判断命令行参数是否给定了PIN脚编号 */
+    if (argc == 2)
+    {
+        pin_num = atoi(argv[1]);
+    }
+    else
+    {
+        pin_num = LED_PIN_NUM;
+    }
+
+    tid = rt_thread_create("led",
+                           led_entry,
+                           RT_NULL,
+                           512,
+                           RT_THREAD_PRIORITY_MAX/3,
+                           20);
+    if (tid != RT_NULL)
+    {
+        rt_thread_startup(tid);
+    }
+}
+/* 导出到 msh 命令列表中 */
+MSH_CMD_EXPORT(led_sample, led sample);

+ 127 - 0
sd_sample.c

@@ -0,0 +1,127 @@
+/*
+ * Copyright (c) 2006-2018, RT-Thread Development Team
+ *
+ * SPDX-License-Identifier: Apache-2.0
+ *
+ * Change Logs:
+ * Date           Author       Notes
+ * 2018-09-25     misonyo      first edition.
+ */
+/* 
+ * 程序清单:这是一个通过SD卡设备的使用例程
+ * 例程导出了 sd_sample 命令到控制终端
+ * 命令调用格式:sd_sample sd0
+ * 命令解释:命令第二个参数是要使用的SD设备的名称,为空则使用例程默认的SD设备。
+ * 程序功能:程序会产生一个块大小的随机数,然后写入SD卡中,然后在读取这部分写入的数据。
+ *            对比写入和读出的数据是否一致,一致则表示程序运行正确。
+*/
+
+#include <rtthread.h>
+#include <rtdevice.h>
+#include <stdlib.h>
+
+#define SD_DEVICE_NAME    "sd0"
+
+void fill_buffer(rt_uint8_t *buff, rt_uint32_t buff_length)
+{
+    rt_uint32_t index;
+    /* 往缓冲区填充随机数 */
+    for (index = 0; index < buff_length; index++)
+    {
+        buff[index] = ((rt_uint8_t)rand()) & 0xff;
+    }
+}
+
+static rt_err_t sd_sample(int argc, char *argv[])
+{  
+	rt_err_t result;
+    rt_device_t sd_device;
+    char sd_name[RT_NAME_MAX];
+    rt_uint8_t* write_buff, *read_buff;
+    struct rt_device_blk_geometry geo;
+	rt_uint8_t block_num;
+    /* 判断命令行参数是否给定了设备名称 */
+    if (argc == 2)
+    {
+        rt_strncpy(sd_name, argv[1], RT_NAME_MAX);
+    }
+    else
+    {
+        rt_strncpy(sd_name, SD_DEVICE_NAME, RT_NAME_MAX);
+    }    
+    /* 查找设备获取设备句柄 */
+    sd_device = rt_device_find(sd_name);
+    if (sd_device == RT_NULL)
+    {
+        rt_kprintf("find device %s failed!\n", sd_name);
+        return RT_ERROR;
+    }
+    /* 打开设备 */
+    result = rt_device_open(sd_device, RT_DEVICE_OFLAG_RDWR);
+    if( result != RT_EOK )
+    {
+        rt_kprintf("open device %s failed!\n", sd_name);
+        return result;
+    }
+    
+    rt_memset(&geo, 0, sizeof(geo));
+    /* 获取块设备信息 */
+    result = rt_device_control(sd_device, RT_DEVICE_CTRL_BLK_GETGEOME, &geo);
+     if( result != RT_EOK )
+    {
+        rt_kprintf("control device %s failed!\n", sd_name);
+        return result;
+    }
+    rt_kprintf("device information:\n");
+    rt_kprintf("sector  size : %d byte\n", geo.bytes_per_sector);
+    rt_kprintf("sector count : %d \n", geo.sector_count);
+    rt_kprintf("block   size : %d byte\n", geo.block_size);
+    /* 准备读写缓冲区空间,大小为一个块 */
+    read_buff = rt_malloc(geo.block_size);
+    if( read_buff == RT_NULL )
+    {
+        rt_kprintf("no memory for read buffer!\n");
+        return RT_ERROR;
+    }
+    write_buff = rt_malloc(geo.block_size);
+    if( write_buff == RT_NULL )
+    {
+        rt_kprintf("no memory for write buffer!\n");
+        rt_free(read_buff);
+        return RT_ERROR;
+    }
+    
+    /* 填充写数据缓冲区,为写操作做准备 */
+    fill_buffer(write_buff, geo.block_size);
+    
+    /* 把写数据缓冲的数据写入SD卡中,大小为一个块,size参数以块为单位 */
+    block_num = rt_device_write(sd_device, 0, write_buff, 1);
+    if (1 != block_num)
+    {
+        rt_kprintf("write device %s failed!\n",sd_name);
+    }
+    
+    /* 从SD卡中读出数据,并保存在读数据缓冲区中 */
+    block_num = rt_device_read(sd_device, 0, read_buff, 1);
+    if (1 != block_num)
+    {
+        rt_kprintf("read %s device failed!\n",sd_name);
+    }
+    
+    /* 比较写数据缓冲区和读数据缓冲区的内容是否完全一致 */
+    if (rt_memcmp(write_buff, read_buff, geo.block_size) == 0)
+    {
+        rt_kprintf("Block test OK!\n");
+    }
+    else
+    {
+        rt_kprintf("Block test Fail!\n");
+    }
+   /* 释放缓冲区空间 */ 
+    rt_free(read_buff);
+    rt_free(write_buff);
+    
+    return RT_EOK;
+}
+/* 导出到 msh 命令列表中 */
+MSH_CMD_EXPORT(sd_sample, sd device sample);