亚洲av成人无遮挡网站在线观看,少妇性bbb搡bbb爽爽爽,亚洲av日韩精品久久久久久,兔费看少妇性l交大片免费,无码少妇一区二区三区

  免費(fèi)注冊(cè) 查看新帖 |

Chinaunix

  平臺(tái) 論壇 博客 文庫(kù)
最近訪問(wèn)板塊 發(fā)新帖
查看: 2670 | 回復(fù): 2
打印 上一主題 下一主題

[其他] 還是乖乖的用va_arg()吧 [復(fù)制鏈接]

論壇徽章:
13
程序設(shè)計(jì)版塊每日發(fā)帖之星
日期:2016-06-29 06:20:00每日論壇發(fā)貼之星
日期:2016-08-14 06:20:00操作系統(tǒng)版塊每日發(fā)帖之星
日期:2016-08-14 06:20:00每日論壇發(fā)貼之星
日期:2016-08-13 06:20:00數(shù)據(jù)庫(kù)技術(shù)版塊每日發(fā)帖之星
日期:2016-08-13 06:20:00程序設(shè)計(jì)版塊每日發(fā)帖之星
日期:2016-08-13 06:20:00IT運(yùn)維版塊每日發(fā)帖之星
日期:2016-08-13 06:20:00每日論壇發(fā)貼之星
日期:2016-08-12 06:20:00數(shù)據(jù)庫(kù)技術(shù)版塊每日發(fā)帖之星
日期:2016-08-12 06:20:00程序設(shè)計(jì)版塊每日發(fā)帖之星
日期:2016-08-12 06:20:00操作系統(tǒng)版塊每日發(fā)帖之星
日期:2016-08-12 06:20:00綜合交流區(qū)版塊每日發(fā)帖之星
日期:2016-08-09 06:20:00
跳轉(zhuǎn)到指定樓層
1 [收藏(0)] [報(bào)告]
發(fā)表于 2017-06-05 23:43 |只看該作者 |倒序?yàn)g覽
本帖最后由 karma303 于 2017-06-05 23:47 編輯

我之前實(shí)現(xiàn)可變參數(shù)的函數(shù),像void foobar( sdf, ...),都是用很土的方式:
unsigned *parg = &sdf; (或是別的什么類(lèi)型,一般都因地制宜)
然后parg[1], parg[2]...一個(gè)個(gè)來(lái)訪問(wèn)!∫矝](méi)出過(guò)什么差錯(cuò)。
今天終于遭報(bào)應(yīng)了,一個(gè)bug調(diào)了至少有4個(gè)小時(shí)。

簡(jiǎn)單點(diǎn)兒說(shuō),就是foobar的堆棧布局,不再是我想象的那樣經(jīng)典的C堆棧布局:
  1. |__sdf __|
  2. |_arg1__|
  3. |_arg2__|
  4. |___.____|
復(fù)制代碼


是跟蹤了跟蹤了匯編碼才發(fā)現(xiàn),foobar的調(diào)用代碼,還是經(jīng)典的C參數(shù)入棧的方式,但進(jìn)入foobar之后,gcc做了一些處理,例如把sdf復(fù)制到新的棧幀,等等?傊畬(dǎo)致sdf下方不再是__VA_ARGS__了。導(dǎo)致只能用va_start/va_arg/va_end來(lái)訪問(wèn)。

最后把今天這段出bug的代碼貼上吧(好像沒(méi)必要,不過(guò)還是貼上吧)。
  1. void __tprobe(struct timeval *base, struct timeval *last,  ...){
  2.     long *interval, *gone;
  3.     struct timeval now;
  4.     gettimeofday(&now, 0);

  5.     va_list vp;
  6.     va_start(vp, last);
  7.     interval = va_arg(vp, long *);
  8.     if(interval){
  9.         *interval = (now.tv_sec - last->tv_sec) * 1000000+
  10.                             now.tv_usec - last->tv_usec;
  11.         gone = va_arg(vp, long *);
  12.         if(gone){
  13.             *gone = (now.tv_sec - base->tv_sec)*1000000+
  14.                             now.tv_usec - base->tv_usec;
  15.         }
  16.     }
  17.     va_end(vp);
  18.     *last = now;
  19. }
復(fù)制代碼
  1. #include<sys/time.h>
  2. #define TSTAMP_INIT()\
  3.     struct timeval __tm_base;\
  4.     struct timeval __tm_last;\
  5.     gettimeofday(&__tm_base, 0)

  6. /* call like this:
  7. * TSTAMP()                just make a timestamp. do nothing else.
  8. * TSTAMP(interval)        make timestamp, and query interval to the latest TSTAMP()
  9. * TSTAMP(interval, gone)    and query how many useconds had gone since TSTAMP_INIT
  10. *
  11. * The arguments @interval, @gone should be a (long *)pointer for storing result
  12. */
  13. #define TSTAMP(...)\
  14.     __tprobe(&__tm_base, &__tm_last,##__VA_ARGS__ ,0)

復(fù)制代碼

之前一直不愿意用va_arg(),一是學(xué)不會(huì),二是是想鍛煉自己多動(dòng)手。現(xiàn)在好了,終于死心了。

論壇徽章:
11
摩羯座
日期:2013-09-29 17:39:09白羊座
日期:2014-11-13 09:38:14技術(shù)圖書(shū)徽章
日期:2014-01-17 15:07:36獅子座
日期:2013-12-25 14:01:52技術(shù)圖書(shū)徽章
日期:2013-12-17 11:33:22技術(shù)圖書(shū)徽章
日期:2013-12-03 10:27:57天秤座
日期:2013-11-08 15:47:19申猴
日期:2013-10-29 13:16:32未羊
日期:2013-10-12 22:28:56辰龍
日期:2013-10-09 14:39:5515-16賽季CBA聯(lián)賽之山東
日期:2016-07-25 10:23:00
2 [報(bào)告]
發(fā)表于 2017-06-08 12:55 |只看該作者
樓主很給力哈

論壇徽章:
7
IT運(yùn)維版塊每日發(fā)帖之星
日期:2016-05-27 06:20:00IT運(yùn)維版塊每日發(fā)帖之星
日期:2016-06-09 06:20:00操作系統(tǒng)版塊每日發(fā)帖之星
日期:2016-06-12 06:20:00程序設(shè)計(jì)版塊每日發(fā)帖之星
日期:2016-06-12 06:20:00操作系統(tǒng)版塊每日發(fā)帖之星
日期:2016-06-13 06:20:00IT運(yùn)維版塊每日發(fā)帖之星
日期:2016-06-17 06:20:002015-2016NBA季后賽紀(jì)念章
日期:2016-06-28 17:42:27
3 [報(bào)告]
發(fā)表于 2017-06-13 11:40 |只看該作者
出錯(cuò)的代碼呢? 帖的是正確的吧
您需要登錄后才可以回帖 登錄 | 注冊(cè)

本版積分規(guī)則 發(fā)表回復(fù)

  

北京盛拓優(yōu)訊信息技術(shù)有限公司. 版權(quán)所有 京ICP備16024965號(hào)-6 北京市公安局海淀分局網(wǎng)監(jiān)中心備案編號(hào):11010802020122 niuxiaotong@pcpop.com 17352615567
未成年舉報(bào)專區(qū)
中國(guó)互聯(lián)網(wǎng)協(xié)會(huì)會(huì)員  聯(lián)系我們:huangweiwei@itpub.net
感謝所有關(guān)心和支持過(guò)ChinaUnix的朋友們 轉(zhuǎn)載本站內(nèi)容請(qǐng)注明原作者名及出處

清除 Cookies - ChinaUnix - Archiver - WAP - TOP