查看: 3976|回复: 3

来个宏定义玩玩,呵呵~

[复制链接]
发表于 2009-7-14 16:38:37 | 显示全部楼层 |阅读模式
关键词: 定义
从驱动接口宏定义抽出来

第一个数据结构


// Driver functions:驱动函数
CYG_ADC_FUNCTIONS( lpc2xxx_adc_funs,
                   lpc2xxx_adc_enable,
                   lpc2xxx_adc_disable,
                   lpc2xxx_adc_set_rate );

//doc中的解释说明
The macro CYG_ADC_FUNCTIONS() instantiates a function table called example_adc_funs and populates it with the ADC driver functions



//宏定义原型

#define CYG_ADC_FUNCTIONS( __name, __enable, __disable, __set_rate )    \
cyg_adc_functions __name =                                              \
{                                                                                         \
    .enable               = __enable,                                          \
    .disable              = __disable,                                          \
    .set_rate            = __set_rate                                         \
};



//adc函数定义原型,一个结构体包含了三个函数指针

struct cyg_adc_functions
{  
    void (*enable)( cyg_adc_channel *chan );
    void (*disable)( cyg_adc_channel *chan );

    void (*set_rate)( cyg_adc_channel *chan, cyg_uint32 rate );
};


/******************************************************************/
宏展开的结果:定义了一个cyg_adc_funtions包含了函数指针的结构体

cyg_adc_functions  lpc2xxx_adc_funs{

    .enable               =  lpc2xxx_adc_enable,                                    
    .disable              =  lpc2xxx_adc_disable,                           
    .set_rate            =  lpc2xxx_adc_set_rate

}      
/********************************************************************/


//ADC信息的私有数据
static lpc2xxx_adc_info lpc2xxx_adc_info0 =
{
    .base               = CYGARC_HAL_LPC2XXX_REG_AD_BASE,
    .vector             = CYGNUM_HAL_INTERRUPT_TIMER1,
    .intprio            = CYGNUM_DEVS_ADC_ARM_LPC24XX_INTPRIO,
    .int_handle         = 0,
#if CYGPKG_DEVS_ADC_ARM_LPC24XX_DEBUG_LEVEL > 0
    .isr_cnt            = 0,
#endif
    .chan_mask          = 0
};

//ADC驱动的总结构,包含了上述的两部分驱动函数和私有数据
CYG_ADC_DEVICE( lpc2xxx_adc_device,               //名字
                &lpc2xxx_adc_funs,                                 //驱动函数
                &lpc2xxx_adc_info0,                                //驱动信息私有数据
                CYGNUM_DEVS_ADC_ARM_LPC24XX_DEFAULT_RATE);    //默认采样率
宏定义
#define CYG_ADC_DEVICE(__name, __funs, __dev_priv, __rate )     \
cyg_adc_device __name =                                         \
{                                                               \
    .funs                    = __funs,                               \
    .dev_priv             = __dev_priv,                           \
    .config.rate         = __rate,                               \
    .init               = false                                 \
};

/********************************************************************************************/
展开宏定义的结果

cyg_adc_device lpc2xxx_adc_device =                                             \
{                                                                                                            \
    .funs                   = lpc2xxx_adc_funs, ,                                            \
    .dev_priv            = lpc2xxx_adc_info0,                                             
    .config.rate          =CYGNUM_DEVS_ADC_ARM_LPC24XX_DEFAULT_RATE,                                         
    .init                      = false                                                                     
};
/**********************************************************************************************/


//ADC0~7驱动的注册
LPC2XXX_ADC_CHANNEL(0~7)

//原型
#define LPC2XXX_ADC_CHANNEL( __chan )                                    \
CYG_ADC_CHANNEL( lpc2xxx_adc_channel##__chan,                            \
                 __chan,                                                 \
                 CYGDAT_DEVS_ADC_ARM_LPC24XX_CHANNEL##__chan##_BUFSIZE,  \
                 &lpc2xxx_adc_device );                                  \
                                                                         \
DEVTAB_ENTRY( lpc2xxx_adc_channel##__chan##_device,                      \
              CYGDAT_DEVS_ADC_ARM_LPC24XX_CHANNEL##__chan##_NAME,        \
              0,                                                         \
              &cyg_io_adc_devio,                                         \
              lpc2xxx_adc_init,                                          \
              lpc2xxx_adc_lookup,                                        \
              &lpc2xxx_adc_channel##__chan );

(1)第一步展开,将"##__chan"和"##_chan##"替换为__chan的数值,假设为0

CYG_ADC_CHANNEL( lpc2xxx_adc_channel0,                                        \
                 0,                                                                                                  \
                 CYGDAT_DEVS_ADC_ARM_LPC24XX_CHANNEL0_BUFSIZE,  \
                 &lpc2xxx_adc_device );                                                            \
                                                                                                                    \
DEVTAB_ENTRY( lpc2xxx_adc_channel0_device,                                 \
              CYGDAT_DEVS_ADC_ARM_LPC24XX_CHANNEL0_NAME,        \
              0,                                                                                                 \
              &cyg_io_adc_devio,                                                                      \
              lpc2xxx_adc_init,                                                                             \
              lpc2xxx_adc_lookup,                                                                       \
              &lpc2xxx_adc_channel0 );


//CYG_ADC_CHANNEL宏定义原型
#define CYG_ADC_CHANNEL( __name, __channel, __bufsize, __device )      
static cyg_adc_sample_t __name##_buf[__bufsize];                                    
cyg_adc_channel __name =                                                                              
{                                                                                                                          
    .channel            = __channel,                                    \
    .buf                = __name##_buf,                                 \
    .len                = __bufsize,                                    \
    .put                = 0,                                            \
    .get                = 0,                                            \
    .device             = __device,                                     \
    .init               = false                                         \
};


(2-1)CYG_ADC_CHANNLE再次展开后的结果:
static cyg_adc_sample_t lpc2xxx_adc_channel0_buf[CYGDAT_DEVS_ADC_ARM_LPC24XX_CHANNEL0_BUFSIZE];                        \
cyg_adc_channel lpc2xxx_adc_channel0 =                                                                   \
{                                                                                                                                        \
    .channel            = 0,                                                                                                     \
    .buf                    = lpc2xxx_adc_channel0_buf,                                                           \
    .len                    = CYGDAT_DEVS_ADC_ARM_LPC24XX_CHANNEL0_BUFSIZE,       \
    .put                   = 0,                                                                           \
    .get                   = 0,                                                                           \
    .device              = &lpc2xxx_adc_device,                                                           \
    .init                    = false                                                                         \
};


(2-2)DEVTAB_ENTRY宏定义的原型
         
    #define DEVTAB_ENTRY(_l,_name,_dep_name,_handlers,_init,_lookup,_priv) \
                   CHAR_DEVTAB_ENTRY(_l,_name,_dep_name,_handlers,_init,_lookup,_priv)
    #define CHAR_DEVTAB_ENTRY(_l,_name,_dep_name,_handlers,_init,_lookup,_priv)  
       cyg_devtab_entry_t _l CYG_HAL_TABLE_ENTRY(devtab) = {                  
       _name,                                                               
       _dep_name,                                                           
       _handlers,                                                           
       _init,                                                               
       _lookup,                                                            
       _priv,                                                               
       CYG_DEVTAB_STATUS_CHAR                                               
    };
           
        展开结果
          cyg_devtab_entry_t _l CYG_HAL_TABLE_ENTRY(devtab) = {                  
       lpc2xxx_adc_channel0_device,                                                                                                        
       CYGDAT_DEVS_ADC_ARM_LPC24XX_CHANNEL0_NAME,                                                                                               
       0,                                                                                                   
       lpc2xxx_adc_init,                                                                                          
       lpc2xxx_adc_lookup,                                                                             
       &lpc2xxx_adc_channel0,                                                                              
       CYG_DEVTAB_STATUS_CHAR                                               
    };      
      CYG_HAL_TABLE_ENTRY()原型
    #define CYG_HAL_TABLE_ENTRY( _name ) \
                CYGBLD_ATTRIB_SECTION(".ecos.table." __xstring(_name) ".data")
            CYGBLD_ATTRIB_USED

      展开结果
                CYGBLD_ATTRIB_SECTION(".ecos.table.devtab.data")
            CYGBLD_ATTRIB_USED
      CYGBLD_ATTRIB_SECTION原型
        #define CYGBLD_ATTRIB_SECTION(__sect__) __attribute__((section (__sect__)))
      展开结果
       __attribute__((section (".ecos.table.devtab.data")))
       展开CYGBLD_ATTRIB_USED
    __attribute__((used))

    CYG_HAL_TABLE_ENTRY()的展开结果为
      __attribute__((section (".ecos.table.devtab.data")))
    __attribute__((used))
    DEVTAB_ENTRY的展开结果为
          cyg_devtab_entry_t _l  __attribute__((section (".ecos.table.devtab.data"))) __attribute__((used)) = {                  
           lpc2xxx_adc_channel0_device,                                                                                                            
           CYGDAT_DEVS_ADC_ARM_LPC24XX_CHANNEL0_NAME,                                                                                               
           0,                                                                                                                                    
           lpc2xxx_adc_init,                                                                                                   
           lpc2xxx_adc_lookup,                                                                                                
           &lpc2xxx_adc_channel0,                                                                                       
           CYG_DEVTAB_STATUS_CHAR                                                                                   
    };      



总结LPC2XXX_ADC_CHANNEL(0)的宏定义结果为
static cyg_adc_sample_t lpc2xxx_adc_channel0_buf[CYGDAT_DEVS_ADC_ARM_LPC24XX_CHANNEL0_BUFSIZE];                        
cyg_adc_channel lpc2xxx_adc_channel0 =                                                                  
{                                                                                                                                       
    .channel            = 0,                                                                                                     
    .buf                    = lpc2xxx_adc_channel0_buf,                                                           
    .len                    = CYGDAT_DEVS_ADC_ARM_LPC24XX_CHANNEL0_BUFSIZE,      
    .put                   = 0,                                                                           
    .get                   = 0,                                                                           
    .device              = &lpc2xxx_adc_device,                                                           
    .init                    = false                                                                        
};

cyg_devtab_entry_t _l  __attribute__((section (".ecos.table.devtab.data"))) __attribute__((used)) = {                  
           lpc2xxx_adc_channel0_device,                                                                                                            
          CYGDAT_DEVS_ADC_ARM_LPC24XX_CHANNEL0_NAME,                                                                 
           0,                                                                                                                                
           lpc2xxx_adc_init,                                                                                                   
           lpc2xxx_adc_lookup,                                                                                                
           &lpc2xxx_adc_channel0,                                                                                          
           CYG_DEVTAB_STATUS_CHAR                                                                                   
    };      



   


因为公社的版本太窄了,导致很多行都乱了,所以把一些还行符删掉了~
看人家老外做的程序,专业~看不懂~
我要是分析的不对的,大家指正
 楼主| 发表于 2009-7-14 16:44:58 | 显示全部楼层
自己沙发,消灭0回复
 楼主| 发表于 2009-7-16 09:39:13 | 显示全部楼层
果然是没人看
发表于 2009-8-25 13:24:48 | 显示全部楼层
cyg_adc_functions  lpc2xxx_adc_funs{

    .enable               =  lpc2xxx_adc_enable,                                    
    .disable              =  lpc2xxx_adc_disable,                           
    .set_rate            =  lpc2xxx_adc_set_rate

}      
看不懂,为何要加个点(.enable)
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

关于我们  -  服务条款  -  使用指南  -  站点地图  -  友情链接  -  联系我们
电子工程网 © 版权所有   京ICP备16069177号 | 京公网安备11010502021702
快速回复 返回顶部 返回列表