新發基金的好處和壞處是什么?新基金的封閉期一般是多久?
新發基金的好處和壞處是什么?新發基金的優點:1、認購費率低:一般
2023/07/06
一、前言
以STM32為例,打開網絡上下載的例程或者是購買開發板自帶的例程,都會發現應用層中會有stm32f10x.h或者stm32f10x_gpio.h,這些文件嚴格來時屬于硬件層的,如果軟件層出現這些文件會顯得很亂。
使用過Linux的童鞋們肯定知道linux系統無法直接操作硬件層,打開linux或者rt_thread代碼會發現代碼中都會有device的源文件,沒錯,這就是驅動層。
(相關資料圖)
二、實現原理
原理就是將硬件操作的接口全都放到驅動鏈表上,在驅動層實現device的open、read、write等操作。當然這樣做也有弊端,就是驅動find的時候需要遍歷一遍驅動鏈表,這樣會增加代碼運行時間。
三、代碼實現
國際慣例,寫代碼先寫頭文件。rt_thread中使用的是雙向鏈表,為了簡單在這我只用單向鏈表。有興趣的可以自行研究rt_thread
頭文件接口:
本次只實現如下接口,device_open 和device_close等剩下的接口可以自行研究。這樣就可以在應用層中只調用如下接口可實現:
/*驅動注冊*/intcola_device_register(cola_device_t*dev);/*驅動查找*/cola_device_t*cola_device_find(constchar*name);/*驅動讀*/intcola_device_read(cola_device_t*dev,intpos,void*buffer,intsize);/*驅動寫*/intcola_device_write(cola_device_t*dev,intpos,constvoid*buffer,intsize);/*驅動控制*/intcola_device_ctrl(cola_device_t*dev,intcmd,void*arg);;
頭文件cola_device.h:
#ifndef_COLA_DEVICE_H_#define_COLA_DEVICE_H_enumLED_state{LED_OFF,LED_ON,LED_TOGGLE,};typedefstructcola_devicecola_device_t;structcola_device_ops{int(*init)(cola_device_t*dev);int(*open)(cola_device_t*dev,intoflag);int(*close)(cola_device_t*dev);int(*read)(cola_device_t*dev,intpos,void*buffer,intsize);int(*write)(cola_device_t*dev,intpos,constvoid*buffer,intsize);int(*control)(cola_device_t*dev,intcmd,void*args);};structcola_device{constchar*name;structcola_device_ops*dops;structcola_device*next;};/*驅動注冊*/intcola_device_register(cola_device_t*dev);/*驅動查找*/cola_device_t*cola_device_find(constchar*name);/*驅動讀*/intcola_device_read(cola_device_t*dev,intpos,void*buffer,intsize);/*驅動寫*/intcola_device_write(cola_device_t*dev,intpos,constvoid*buffer,intsize);/*驅動控制*/intcola_device_ctrl(cola_device_t*dev,intcmd,void*arg);#endif
源文件cola_device.c:
#include"cola_device.h"#include#include structcola_device*device_list=NULL;/*查找任務是否存在*/staticboolcola_device_is_exists(cola_device_t*dev){cola_device_t*cur=device_list;while(cur!=NULL){if(strcmp(cur->name,dev->name)==0){returntrue;}cur=cur->next;}returnfalse;}staticintdevice_list_inster(cola_device_t*dev){cola_device_t*cur=device_list;if(NULL==device_list){device_list=dev;dev->next=NULL;}else{while(NULL!=cur->next){cur=cur->next;}cur->next=dev;dev->next=NULL;}return1;}/*驅動注冊*/intcola_device_register(cola_device_t*dev){if((NULL==dev)||(cola_device_is_exists(dev))){return0;}if((NULL==dev->name)||(NULL==dev->dops)){return0;}returndevice_list_inster(dev);}/*驅動查找*/cola_device_t*cola_device_find(constchar*name){cola_device_t*cur=device_list;while(cur!=NULL){if(strcmp(cur->name,name)==0){returncur;}cur=cur->next;}returnNULL;}/*驅動讀*/intcola_device_read(cola_device_t*dev,intpos,void*buffer,intsize){if(dev){if(dev->dops->read){returndev->dops->read(dev,pos,buffer,size);}}return0;}/*驅動寫*/intcola_device_write(cola_device_t*dev,intpos,constvoid*buffer,intsize){if(dev){if(dev->dops->write){returndev->dops->write(dev,pos,buffer,size);}}return0;}/*驅動控制*/intcola_device_ctrl(cola_device_t*dev,intcmd,void*arg){if(dev){if(dev->dops->control){returndev->dops->control(dev,cmd,arg);}}return0;}
硬件注冊方式:以LED為例,初始化接口void led_register(void),需要在初始化中調用。
#include"stm32f0xx.h"#include"led.h"#include"cola_device.h"#definePORT_GREEN_LEDGPIOC#definePIN_GREENLEDGPIO_Pin_13/*LED亮、滅、變化*/#defineLED_GREEN_OFF(PORT_GREEN_LED->BSRR=PIN_GREENLED)#defineLED_GREEN_ON(PORT_GREEN_LED->BRR=PIN_GREENLED)#defineLED_GREEN_TOGGLE(PORT_GREEN_LED->ODR^=PIN_GREENLED)staticcola_device_tled_dev;staticvoidled_gpio_init(void){GPIO_InitTypeDefGPIO_InitStructure;RCC_AHBPeriphClockCmd(RCC_AHBPeriph_GPIOC,ENABLE);GPIO_InitStructure.GPIO_Pin=PIN_GREENLED;GPIO_InitStructure.GPIO_Mode=GPIO_Mode_OUT;GPIO_InitStructure.GPIO_Speed=GPIO_Speed_50MHz;GPIO_InitStructure.GPIO_OType=GPIO_OType_PP;GPIO_InitStructure.GPIO_PuPd=GPIO_PuPd_NOPULL;GPIO_Init(PORT_GREEN_LED,&GPIO_InitStructure);LED_GREEN_OFF;}staticintled_ctrl(cola_device_t*dev,intcmd,void*args){if(LED_TOGGLE==cmd){LED_GREEN_TOGGLE;}else{}return1;}staticstructcola_device_opsops={.control=led_ctrl,};voidled_register(void){led_gpio_init();led_dev.dops=&ops;led_dev.name="led";cola_device_register(&led_dev);}
應用層app代碼:
#include#include"app.h"#include"config.h"#include"cola_device.h"#include"cola_os.h"statictask_ttimer_500ms;staticcola_device_t*app_led_dev;//led每500ms狀態改變一次staticvoidtimer_500ms_cb(uint32_tevent){cola_device_ctrl(app_led_dev,LED_TOGGLE,0);}voidapp_init(void){app_led_dev=cola_device_find("led");assert(app_led_dev);cola_timer_create(&timer_500ms,timer_500ms_cb);cola_timer_start(&timer_500ms,TIMER_ALWAYS,500);}
這樣app.c文件中就不需要調用led.h頭文件了,rtt就是這樣實現的。
四、總結
這樣就可以實現軟硬件分層了,是不是非常好用!
審核編輯:湯梓紅標簽: