2013-06-05 10 views
0

誰能告訴,在我的代碼塊後while(k - ){},爲什麼(t1-t0)= 0?
誰可以幫助在其他機器上嘗試相同的代碼,看它是否顯示相同的問題?
我的機器是惠普筆記本與
CPU:英特爾P9300 2.26GHz的X 2,
4GB內存,
操作系統:Ubuntu的12.04,
Linux內核:3.2.0-45-通用。
這個腳本是gwan的main.c。gwan getus()getns()不正確的結果?

typedef struct 
{ 
    u64 a[10000000], b[10000000], c[10000000]; 

} data_t; 

char str[512]; 
u64 size; 



int main(int argc, char *argv[]) 
{ 

    data_t **data = (data_t**)get_env(argv, US_SERVER_DATA); 
             // US_VHOST_DATA); 

    if(!*data) // first time: persistent pointer is uninitialized 
    { 
     *data = (data_t*)calloc(1, sizeof(data_t)); 
     if(!*data) return 500; // out of memory 
     size = sizeof(data_t); 
     s_snprintf(str, sizeof(str)-1, "initialized data: %llu Bytes", size); 
     puts(str); 
    } 


    u64 t0, t1, timea, timeb, timediff, va, vb, vc, wa, wb, wc; 
    u64 m, j, n, k; 

    for(;;) 
    //int i=10; while(i--) 
    { 
     sleep(1); 
     //t1=0;time=0; 
     m=10000000; j=m; 
     t0 = getms(); 
     while(j--){ 
     va = __sync_add_and_fetch(&(*data)->a[1], 1); 
     vb = __sync_add_and_fetch(&(*data)->b[2], 2); 
     vc = __sync_add_and_fetch(&(*data)->c[3], 3); 
     } 
     t1 = getms(); 
     timediff = t1-t0; 
     timea = timediff ? (3*m)/(t1-t0) : m; 
 // problem code below: 
 n=m; k=n; 
     t0 = getns(); 
     while(k--){ 
     wa++; 
     wa--; 
     wa++; 
     wa--; 
     } 
     t1 = getns(); 
     timediff = t1-t0; 
     timeb = timediff ? (4*n)/(t1-t0) : n; 

     //s_snprintf(str, sizeof(str) - 1, "data[0]->a[1]:%llu, data[0]->b[2]:%llu, data[0]->c[3]:%llu, atomic add:%llu/ms, val++:%llu/ms", 
             //data[0]->a[1],  data[0]->b[2],  data[0]->c[3],  timea, timeb); 
             //va,  vb,  vc,  timea, timeb); 
     s_snprintf(str, sizeof(str) - 1, "atomic add:%llu/ms, ++val:%llu/ns, end value:%llu", 
                timea,   timeb,   wa); 
     puts(str); 
    } 
    return 0; 

如下日誌文件:在納秒

initialized data: 240000000 Bytes 
[Wed Jun 05 04:57:17 2013 GMT] memory footprint: 5.28 MiB. 
atomic add:35377/ms, ++val:19531/ns, end value:0 
atomic add:30674/ms, ++val:39062/ns, end value:0 
atomic add:86206/ms, ++val:10000000/ns, end value:0 
atomic add:86455/ms, ++val:10000000/ns, end value:0 
atomic add:48309/ms, ++val:10000000/ns, end value:0 
atomic add:30706/ms, ++val:10000000/ns, end value:0 
atomic add:30674/ms, ++val:10000000/ns, end value:0 
atomic add:30674/ms, ++val:10000000/ns, end value:0 
atomic add:86705/ms, ++val:10000000/ns, end value:0 
atomic add:86455/ms, ++val:10000000/ns, end value:0 
atomic add:86455/ms, ++val:10000000/ns, end value:0 
atomic add:61099/ms, ++val:10000000/ns, end value:0 
atomic add:50167/ms, ++val:10000000/ns, end value:0 
... 

只有前兩個結果放映有意義的數據。其餘全部爲++ val:10000000/ns,即t1-t0 = 0.
與getus()相同的問題。
當我使用getms()時,t1-t0總是等於0.
注意:第二行是第一行的兩倍,即19531/ns x 2 = 39062/ns。

回答

0

爲什麼(t1-t0)= 0?

此代碼不是特別容易閱讀。

爲什麼不開始打印時間值(而不是他們的差異)?然後,我們將看到爲什麼差異爲空。

它可能是時間分辨率太低(使連續值相等)或API調用失敗(返回0)。

您的機器上是否有httpdate.c G-WAN示例工作?

0

[已解決]
getns()沒有問題。
Plz查看鏈接:https://stackoverflow.com/a/11609063/1796259
我將wa更改爲volatile,並將timediff,timea,timeb更改爲float類型。
它給了我下面的正確的結果:

atomic add:63829.789062/ms, ++val:0.375601/ns, end value:0 
atomic add:63829.789062/ms, ++val:0.376809/ns, end value:0 
atomic add:76923.078125/ms, ++val:0.375601/ns, end value:0 
atomic add:78947.367188/ms, ++val:0.373209/ns, end value:0 
atomic add:78947.367188/ms, ++val:0.375601/ns, end value:0 
atomic add:73170.734375/ms, ++val:0.378024/ns, end value:0 
atomic add:78947.367188/ms, ++val:0.375601/ns, end value:0 
atomic add:78947.367188/ms, ++val:0.375601/ns, end value:0 
atomic add:81081.078125/ms, ++val:0.378024/ns, end value:0 
atomic add:81081.078125/ms, ++val:0.375601/ns, end value:0 

++ val爲X5〜6比__syn_add_and_fetch更快。

+0

感謝您發佈答案。考慮到他們的好處,原子操作時機並不糟糕。有時候可能比GCC原子建立更快,因爲它們總是在所有情況下都使用內存屏障來保證安全。通過在asm中構建自己的原子操作,您可以爲需要較少安全性的情況製造麻煩。 – Gil