作者小头像 Lv.1
43 成长值

个人介绍

这个人很懒,什么都没有留下

感兴趣或擅长的领域

编程语言
个人勋章
TA还没获得勋章~
成长雷达
0
3
25
15
0

个人资料

个人介绍

这个人很懒,什么都没有留下

感兴趣或擅长的领域

编程语言

达成规则

发布时间 2021/04/14 14:56:34 最后回复 aarom 2021/04/17 11:45:56 版块 鲲鹏
813 5 0
发布时间 2021/04/16 10:59:46 最后回复 aarom 2021/04/17 11:35:13 版块 鲲鹏
1025 3 0
发布时间 2021/01/21 15:13:35 最后回复 重新来过 2021/01/24 09:35:52 版块 鲲鹏
6071 4 2
他的回复:
---------------------------------------------------------------------atomic.h--------------------------------------------------------------------////=================================================================== // // // Copyright (C) 2010 Taobao.com, Inc. // // ------------------------------------------------------------------- // // Description // // // ------------------------------------------------------------------- //  // Change Log //////====================================================================#ifndef  TFS_COMMON_ATOMIC_H_#define  TFS_COMMON_ATOMIC_H_namespace tfs {  namespace common   {    // Proclaim we are using SMP    #ifndef CONFIG_SMP    # define CONFIG_SMP    #endif        #if defined(__i386__) || defined(__x86_64__)        // Atomic operations that C can't guarantee us.  Useful for    // resource counting etc..    // SMP lock prefix                                                                                                               #ifdef CONFIG_SMP    #define LOCK_PREFIX "lock ; "    #else    #define LOCK_PREFIX ""    #endif    //return: the incremented value;    /// 原子地做 8位,16位,32位,64位的++i的操作    /// 该操作虽然参数和返回值都是无符号型整数,但是一样可以    /// 对有符号型整数做操作,只需要做适当的参数转换即可    /// @param pv 指向操作数的指针    /// @return 操作数加1以后的数值    #ifdef __x86_64__    static __inline__ uint64_t atomic_inc(volatile uint64_t * pv)    {      register unsigned long __res;      __asm__ __volatile__ (          "movq $1,%0;"          LOCK_PREFIX "xaddq %0,(%1);"          "incq %0"          :"=a" (__res), "=q" (pv): "1" (pv));      return __res;    }    #endif        static __inline__ uint32_t atomic_inc(volatile uint32_t * pv)    {      register unsigned int __res;      __asm__ __volatile__ (          "movl $1,%0;"          LOCK_PREFIX "xaddl %0,(%1);"          "incl %0"          :"=a" (__res), "=q" (pv): "1" (pv));      return __res;    }        static __inline__ uint16_t atomic_inc(volatile uint16_t * pv)    {      register unsigned short __res;      __asm__ __volatile__ (          "movw $1,%0;"          LOCK_PREFIX "xaddw %0,(%1);"          "incw %0"          :"=a" (__res), "=q" (pv): "1" (pv));      return __res;        }        static __inline__ uint8_t  atomic_inc(volatile uint8_t * pv)    {      register unsigned char __res;      __asm__ __volatile__ (          "movb $1,%0;"          LOCK_PREFIX "xaddb %0,(%1);"          "incb %0"          :"=a" (__res), "=q" (pv): "1" (pv));      return __res;    }        //return: the decremented value;    /// 原子地做 8位,16位,32位,64位的--i的操作    /// 该操作虽然参数和返回值都是无符号型整数,但是一样可以    /// 对有符号型整数做操作,只需要做适当的参数转换即可    /// @param pv 指向操作数的指针    /// @return 操作数减1后的数值    #ifdef __x86_64__    static __inline__ uint64_t atomic_dec(volatile uint64_t * pv)    {      register unsigned long __res;      __asm__ __volatile__ (          "movq $0xffffffffffffffff,%0;"          LOCK_PREFIX "xaddq %0,(%1);"          "decq %0"          : "=a" (__res), "=q" (pv): "1" (pv));      return __res;        }    #endif    static __inline__ uint32_t atomic_dec(volatile uint32_t * pv)    {      register unsigned int __res;      __asm__ __volatile__ (          "movl $0xffffffff,%0;"          LOCK_PREFIX "xaddl %0,(%1);"          "decl %0"          : "=a" (__res), "=q" (pv): "1" (pv));      return __res;        }    static __inline__ uint16_t atomic_dec(volatile uint16_t * pv)    {      register unsigned short __res;      __asm__ __volatile__ (          "movw $0xffff,%0;"          LOCK_PREFIX "xaddw %0,(%1);"          "decw %0"          : "=a" (__res), "=q" (pv): "1" (pv));      return __res;    }        static __inline__ uint8_t  atomic_dec(volatile uint8_t * pv)    {      register unsigned char __res;      __asm__ __volatile__ (          "movb $0xff,%0;"          LOCK_PREFIX "xaddb %0,(%1);"          "decb %0"          : "=a" (__res), "=q" (pv): "1" (pv));      return __res;    }        //return: the initial value of *pv    /// 原子地做 8位,16位,32位,64位的加法的操作    /// 该操作虽然参数和返回值都是无符号型整数,但是一样可以    /// 对有符号型整数做操作,只需要做适当的参数转换即可    /// @param pv 指向操作数的指针    /// @return 操作数加法之前的数值    #ifdef __x86_64__    static __inline__ uint64_t atomic_add(volatile uint64_t * pv, const uint64_t av)    {      //:"=a" (__res), "=q" (pv): "m"(av), "1" (pv));      register unsigned long __res;      __asm__ __volatile__ (          "movq %2,%0;"          LOCK_PREFIX "xaddq %0,(%1);"          :"=a" (__res), "=q" (pv): "mr"(av), "1" (pv));      return __res;    }    #endif    static __inline__ uint32_t atomic_add(volatile uint32_t * pv, const uint32_t av)    {      //:"=a" (__res), "=q" (pv): "m"(av), "1" (pv));      register unsigned int __res;      __asm__ __volatile__ (          "movl %2,%0;"          LOCK_PREFIX "xaddl %0,(%1);"          :"=a" (__res), "=q" (pv): "mr"(av), "1" (pv));      return __res;    }        static __inline__ uint16_t atomic_add(volatile uint16_t * pv, const uint16_t av)    {      //:"=a" (__res), "=q" (pv): "m"(av), "1" (pv));      register unsigned short __res;      __asm__ __volatile__ (          "movw %2,%0;"          LOCK_PREFIX "xaddw %0,(%1);"          :"=a" (__res), "=q" (pv): "mr"(av), "1" (pv));      return __res;    }        static __inline__ uint8_t  atomic_add(volatile uint8_t * pv, const uint8_t av)    {      //:"=a" (__res), "=q" (pv): "m"(av), "1" (pv));      register unsigned char __res;      __asm__ __volatile__ (          "movb %2,%0;"          LOCK_PREFIX "xaddb %0,(%1);"          :"=a" (__res), "=q" (pv): "mr"(av), "1" (pv));      return __res;    }        //function: set *pv to nv    //return: the initial value of *pv    /// 原子地把nv赋值给pv指向的整数,支持8位,16位,32位,84位操作    /// @param pv 待赋值的整数(目的操作数)    /// @param nv 向pv赋的整数    /// @return pv指向的赋值前的数值    #ifdef __x86_64__    static __inline__ uint64_t atomic_exchange(volatile uint64_t * pv, const uint64_t nv)    {      register unsigned long __res;      __asm__ __volatile__ (          "1:"          LOCK_PREFIX "cmpxchgq %3,(%1);"                \          "jne 1b":           "=a" (__res), "=q" (pv): "1" (pv), "q" (nv), "0" (*pv));      return __res;    }    #endif    static __inline__ uint32_t atomic_exchange(volatile uint32_t * pv, const uint32_t nv)    {      register unsigned int __res;      __asm__ __volatile__ (          "1:"          LOCK_PREFIX "cmpxchgl %3,(%1);"                \          "jne 1b":           "=a" (__res), "=q" (pv): "1" (pv), "q" (nv), "0" (*pv));      return __res;    }        static __inline__ uint16_t atomic_exchange(volatile uint16_t * pv, const uint16_t nv)    {      register unsigned short __res;      __asm__ __volatile__ (          "1:"          LOCK_PREFIX "cmpxchgw %3,(%1);"                \          "jne 1b":           "=a" (__res), "=q" (pv): "1" (pv), "q" (nv), "0" (*pv));      return __res;    }        static __inline__ uint8_t  atomic_exchange(volatile uint8_t * pv, const uint8_t nv)    {      register unsigned char __res;      __asm__ __volatile__ (          "1:"          LOCK_PREFIX "cmpxchgb %3,(%1);"                \          "jne 1b":           "=a" (__res), "=q" (pv): "1" (pv), "q" (nv), "0" (*pv));       return __res;    }        //function: compare *pv to cv, if equal, set *pv to nv, otherwise do nothing.    //return: the initial value of *pv    /// 比较pv和cv,如果两者相等,则返回pv原有数值并且把nv赋值给pv    /// 否则什么也不作,返回pv原有数值    /// @param pv 待赋值的整数(目的操作数)    /// @param nv 向pv赋的整数    /// @param cv 和pv比较的整数    /// @return pv指向的操作前的数值    #ifdef __x86_64__    static __inline__ uint64_t atomic_compare_exchange(volatile uint64_t * pv,         const uint64_t nv, const uint64_t cv)    {      register unsigned long __res;      __asm__ __volatile__ (          LOCK_PREFIX "cmpxchgq %3,(%1)"          : "=a" (__res), "=q" (pv) : "1" (pv), "q" (nv), "0" (cv));      return __res;    }    #endif    static __inline__ uint32_t atomic_compare_exchange(volatile uint32_t * pv,         const uint32_t nv, const uint32_t cv)    {      register unsigned int __res;      __asm__ __volatile__ (          LOCK_PREFIX "cmpxchgl %3,(%1)"          : "=a" (__res), "=q" (pv) : "1" (pv), "q" (nv), "0" (cv));      return __res;    }    static __inline__ uint16_t atomic_compare_exchange(volatile uint16_t * pv,         const uint16_t nv, const uint16_t cv)    {      register unsigned short __res;      __asm__ __volatile__ (          LOCK_PREFIX "cmpxchgw %3,(%1)"          : "=a" (__res), "=q" (pv) : "1" (pv), "q" (nv), "0" (cv));      return __res;    }    static __inline__ uint8_t atomic_compare_exchange(volatile uint8_t * pv,         const uint8_t nv, const uint8_t cv)    {      register unsigned char  __res;      __asm__ __volatile__ (          LOCK_PREFIX "cmpxchgb %3,(%1)"          : "=a" (__res), "=q" (pv) : "1" (pv), "q" (nv), "0" (cv));      return __res;    }        typedef void * pvoid;        //function: set *pv to nv    //return: the initial value of *pv    /// 把nv原子地赋值给*pv    static __inline__ pvoid atomic_exchange_pointer(volatile pvoid * pv, const pvoid nv)    {    #ifdef __x86_64__      return (pvoid) atomic_exchange((uint64_t *) pv, (uint64_t) nv);    #else      return (pvoid) atomic_exchange((uint32_t *) pv, (uint32_t) nv);    #endif    }    //function: compare *pv to cv, if equal, set *pv to nv, otherwise do nothing.    //return: the initial value of *pv    /// 比较cv和*pv,如果两者相等则把nv赋值给*pv,并且返回*pv原有数值    /// 否则返回*pv原有数值,不做赋值操作    static __inline__ pvoid atomic_compare_exchange_pointer(volatile pvoid * pv,         const pvoid nv, const pvoid cv)    {    #ifdef __x86_64__      return (pvoid) atomic_compare_exchange((uint64_t *) pv, (uint64_t) nv, (uint64_t)cv);    #else      return (pvoid) atomic_compare_exchange((uint32_t *) pv, (uint32_t) nv, (uint32_t)cv);    #endif    }        #undef LOCK_PREFIX    #elif defined(__aarch64__)    #define atomic_inc_bytype(ptr,type) \    ({ \  typeof(type) c = __sync_add_and_((ptr),1); \  c ; \})   #define atomic_dec_bytype(ptr,type) \({ \ typeof(type) c = __sync_sub_and_((ptr),1); \ c ; \})   #define atomic_add_bytype(ptr,v,type) \({ \ typeof(type) c = __sync__and_add((ptr),v); \ c ; \   }) #define atomic_exchange(ptr,v,type) \({ \ typeof(type) c = __sync_lock_test_and_set((ptr),v); \ c ; \})   #define atomic_compare_exchange(ptr,newv,oldv,type) \({ \ typeof(type) c = __sync_val_compare_and_swap((ptr),oldv,newv); \ c ; \    })    #else // #if defined(__i386__) || defined(__x86_64__)        #error "must compiled on i386 or x86_64"        #endif //  }}#endif // TFS_COMMON_ATOMIC_H_ -----------------------------------------------------------------------------------------------------------------------------迁移结果如下:到此,整个淘宝的文件系统tfs已经迁移完毕
发布时间 2021/01/20 17:24:02 最后回复 大慧高拍飞 2021/01/21 14:58:18 版块 鲲鹏
1926 5 1
他的回复:
关于修改部分的内容,单独建立个测试单元:测试的代码如下:---------------------------------------------------------------我是分割线-------------------------------------------------------------------------------------------------------atomic_aarch64.h------------------------------------------------------------#ifndef __ATOMIC_AARCH64__#define __ATOMIC_AARCH64__typedef struct { volatile int counter; } atomic_t;#define ATOMIC_INIT(i)  { (i) }#define barrier() __asm__ __volatile__("": : :"memory")typedef unsigned char  __u8_alias_t;typedef unsigned short __u16_alias_t;typedef unsigned int __u32_alias_t;typedef unsigned long long __u64_alias_t;static inline void __read_once_size(const volatile void *p, void *res, int size){    switch (size) {    case 1: *(__u8_alias_t  *) res = *(volatile __u8_alias_t  *) p; break;    case 2: *(__u16_alias_t *) res = *(volatile __u16_alias_t *) p; break;    case 4: *(__u32_alias_t *) res = *(volatile __u32_alias_t *) p; break;    case 8: *(__u64_alias_t *) res = *(volatile __u64_alias_t *) p; break;    default:        barrier();        __builtin_memcpy((void *)res, (const void *)p, size);        barrier();    }}static inline void __write_once_size(volatile void *p, void *res, int size){    switch (size) {    case 1: *(volatile  __u8_alias_t *) p = *(__u8_alias_t  *) res; break;    case 2: *(volatile __u16_alias_t *) p = *(__u16_alias_t *) res; break;    case 4: *(volatile __u32_alias_t *) p = *(__u32_alias_t *) res; break;    case 8: *(volatile __u64_alias_t *) p = *(__u64_alias_t *) res; break;    default:        barrier();        __builtin_memcpy((void *)p, (const void *)res, size);        barrier();    }}#define READ_ONCE(x)                    \({                          \    union { typeof(x) __val; char __c[1]; } __u =   \        { .__c = { 0 } };           \    __read_once_size(&(x), __u.__c, sizeof(x)); \    __u.__val;                  \})#define WRITE_ONCE(x, val)              \({                          \    union { typeof(x) __val; char __c[1]; } __u =   \        { .__val = (val) };             \    __write_once_size(&(x), __u.__c, sizeof(x));    \    __u.__val;                  \})#define atomic_read(v)  READ_ONCE((v)->counter)#define atomic_set(v,i) WRITE_ONCE(((v)->counter), (i))static inline int atomic_add_return(int i, atomic_t *v){        return __sync_add_and_fetch(&v->counter,i);}static inline int atomic_dec(atomic_t *v){        return __sync_sub_and_fetch(&v->counter,1);}static inline void atomic_inc(atomic_t *v){        __sync_add_and_fetch(&v->counter,1);}#endif-------------------------------------------------atomic_aarch64.h-----------------------------------------------------------------------------------------------------------------------------atomic.c--------------------------------------------------------------#include "atomic_aarch64.h"#include #include #include time.h>#include #include #include static atomic_t at={(0)};static int ttime = 0;static uint32_t xx=0;void* test_atomic_add_return(void* param){        time_t t = ttime;        time_t ot = time(NULL);        time_t nt = time(NULL);        uint32_t* j = calloc(1,sizeof(uint32_t));        while( (nt-ot) xx)        {                atomic_add_return(1,&at);                ++(*j);        }        return j;}int main(int argc,char* argv[]){        if(argc2)        {                printf("please input test time!\n");                return -1;        }        ttime = atoi(argv[1]);        atomic_set(&at, 0);        pthread_t tid[4]={0};        for(int i=0;i4;i++)        {                if(pthread_create(&tid[i],NULL,test_atomic_add_return,NULL))                {                        printf("create thread error!\n");                        return -2;                }        }        uint32_t* zj[4]={0};        for(int i=0;i4;i++)        {                pthread_join(tid[i],(void*)&zj[i]);        }        uint32_t st = *zj[0] + *zj[1] + *zj[2] + *zj[3];        printf("TEST atomic_add_return %s\n", atomic_read(&at)==st?"Pass":"Failed");        for(int i=0;i4;i++)        {                free(zj[i]);                zj[i] = NULL;        }        if(atomic_read(&at)!=st)                return -3;        uint32_t sbn = st;        for(int i=0;i4;i++)        {                if(pthread_create(&tid[i],NULL,test_atomic_dec,NULL))                {                        printf("create thread error!\n");                        return -4;                }        }        for(int i=0;i4;i++)        {                pthread_join(tid[i],(void*)&zj[i]);        }        st  = *zj[0] + *zj[1] + *zj[2] + *zj[3];        printf("TEST atomic_dec %s\n", ((sbn-st)==atomic_read(&at))?"Pass":"Failed");        for(int i=0;i4;i++)        {                free(zj[i]);                zj[i] = NULL;        }        xx = 60000;        atomic_set(&at, 0);        for(int i=0;i4;i++)        {                if(pthread_create(&tid[i],NULL,test_atomic_read,NULL))                {                        printf("create thread error!\n");                        return -2;                }        }        for(int i=0;i4;i++)        {                pthread_join(tid[i],(void*)&zj[i]);        }        st  = *zj[0] + *zj[1] + *zj[2] + *zj[3];        printf("TEST atomic_read %s\n",st==atomic_read(&at)?"Pass":"Failed");        for(int i=0;i4;i++)        {                free(zj[i]);                zj[i] = NULL;        }        return 0;}-----------------------------------------------------------------atomic.c--------------------------------------------------------------测试结果如下:    
发布时间 2020/10/29 19:11:09 最后回复 aarom 2021/01/11 16:59:36 版块 迁移调优实践
3665 5 0