/**
 * \file    drv_reg_intf.h
 * \brief   driver register interface
 *
 * \par     Copyright (c) 2018 UWE Technologies Corp., Ltd. All Rights Reserved.
 * \author  James
 * \date    2018-03-01
 * \version 
 * 
 * \history 
 *  Date        Note
 *  2018-03-01  Original Creation
 * 
 */
 
#ifndef __DRV_REG_INTF_H_
#define __DRV_REG_INTF_H_


#include "types.h"

/** Get register */
u32_t drv_reg_get(u32_t reg);

/** Get multiple registers */
void drv_reg_mget(u32_t reg, u32_t cnt, u32_t *p_val);

/** Set register */
void drv_reg_set(u32_t reg, u32_t val);

/** Set multiple registers */
void drv_reg_mset(u32_t reg, u32_t cnt, u32_t *p_val);

/** Get register field with width */
u32_t drv_reg_field_get(u32_t reg, u32_t field, u32_t width);

/** Set register field with width */
void drv_reg_field_set(u32_t reg, u32_t field, u32_t width, u32_t val);

/** Get register field with mask */
u32_t drv_reg_field_get2(u32_t reg, u32_t field, u32_t field_set);

/** Set register field with mask */
void drv_reg_field_set2(u32_t reg, u32_t field, u32_t field_set, u32_t field_mask, u32_t val);

/** Get register */
#define DRV_REG_GET(reg)                        (*(volatile u32_t *)(reg))
/** Set register */
#define DRV_REG_SET(reg,val)                    (*(volatile u32_t *)(reg) = val)
/** Get register */
#define DRV_REG_MGET(reg,cnt,pval)              drv_reg_mget(reg,cnt,pval)
/** Set register */
#define DRV_REG_MSET(reg,cnt,pval)              drv_reg_mset(reg,cnt,pval)
/** Get register field */
#define DRV_REG_FIELD_GET(reg,field)            drv_reg_field_get2(reg,reg##_##field,reg##_##field##_FLDSET)
/** Set register field */
#define DRV_REG_FIELD_SET(reg,field,val)        drv_reg_field_set2(reg,reg##_##field,reg##_##field##_FLDSET,reg##_##field##_FLDMSK,val)
/** Get register field with width */
#define DRV_REG_FIELD_GET2(reg,field,width)     drv_reg_field_get(reg,reg##_##field,width)
/** Set register field with width */
#define DRV_REG_FIELD_SET2(reg,field,width,val) drv_reg_field_set(reg,reg##_##field,width,val)

/** Set register field, for saving instruction */
#define DRV_REG_FIELD_SET3(reg,field,val) \
    do { \
        *(volatile u32_t *)(reg) = ((*(volatile u32_t *)(reg)) & (reg##_##field##_FLDMSK)) | (val); \
    } while (0)

#define DRV_REG_VAL_PLUS(reg,val) \
    do { \
        *(volatile u32_t *)(reg) = *(volatile u32_t *)(reg) | (val); \
    } while (0)

#endif /* #ifndef __DRV_REG_INTF_H_ */

