C_and_CPP 板


LINE

我們先來看一下你定義出來的 struct,在記憶體中長什麼樣。 (假設你的 int 長度也是 16-bit,系統為 little-endian) : typdef struct{ typedef struct{ : int A; int B; : char *data; char userData[8]; : } MSG_OBJ } MSG_OBJ_USE MSG_OBJ MSG_OBJ_USE Address +------------+ +-------------+ x | | | | x+1 | A | | B | +------------+ +-------------+ x+2 | | | userData[0] | x+3 | data | | userData[1] | +------------+ x+4 | userData[2] | x+5 | userData[3] | x+6 | userData[4] | x+7 | userData[5] | x+8 | userData[6] | x+9 | userData[7] | +-------------+ 宣告指標、和宣告陣列,記憶體長得就會不一樣。 然後,我們假設 compiler(實際上是 linker)把你的 globalData[8] 放在 0x9518 這個位置: : char globalData[8] = {0}; Address +---------------+ 0x9518 | globalData[0] | 0x9519 | globalData[1] | : 0x951F | globalData[7] | +---------------+ 然後你的 obj 放在 0x9520: : MSG_OBJ_USE obj; 由於你宣告在 global scope,我們假設整段空間的內容預設都是 0。 : void getDataFun(MSG_OBJ* b) : { : b->data = globalData; : } 接下來這行有些 tricky.... getDataFun() 要接收的是 MSG_OBJ* 但你傳進的去的是 MSG_OBJ_USE* : getDataFun(&obj); 現在大部份的 compiler 會因為 type 不合而發生 error(最少也是 warning), 但如果 compiler 讓你過的話,等於是 「把 0x9520 開始的記憶體空間,當成是 MSG_OBJ 來處理」。 因此,這行執行完後,你的 obj 的內容會變成: MSG_OBJ_USE Address +-------------+ 0x9520 | 0x00 | 0x9521 | 0x00 | +-------------+ 0x9522 | 0x18 | 0x9523 | 0x95 | 0x9524 | 0x00 | 0x9525 | 0x00 | 0x9526 | 0x00 | 0x9527 | 0x00 | 0x9528 | 0x00 | 0x9529 | 0x00 | +-------------+ Why? 因為 getDataFun() 把 0x9520 當成 MSG_OBJ 來處理, 所以就把 globalData 的位址(也就是 0x9518) 填到原本 MSG_OBJ::data 該在的位置(也就是 0x9520+2 & 0x9520+3)。 : char* ptr = (char*)(*(uint16_t*)obj.useData); //平台指標為16 bits 一步一步看: Type Value obj.useData ==> char* 0x9522 (uint16_t*)obj.useData ==> uint16_t* 0x9522 *(uint16_t*)obj.useData ==> uint16_t 0x9518(obj.useData的內容) (char*)*(uint16_t*)obj.useData ==> char* 0x9518 因此 ptr 的內容就是 0x9518,也就是 globalData 的位址。 : //Step.2 : for(int i=0;i<8;i++); : { : obj.useData[i] = ptr[i]; : } 從前面的分析來看,這個 loop 就是把 globalData 的值複製到 obj.userData... 如此而已。 : //問題: : Step1.的動作意思是useData array上面放的值是指標, 所以才可以取值(*)給ptr : 然後用step2把copy資料. : 我的疑問是b->data = globalData應該是把&globalData[0] 指定給b->data而已. 其實我看不懂你的問題。 XD 不過希望前面的分析能幫到你的忙。 --



※ 發信站: 批踢踢實業坊(ptt.cc), 來自: 223.137.47.224 (臺灣)
※ 文章網址: https://webptt.com/m.aspx?n=bbs/C_and_CPP/M.1655461848.A.2E7.html ※ 編輯: closer76 (223.137.47.224 臺灣), 06/17/2022 18:38:20
1F:推 OnlyRD: 通常這種太特殊的寫法,如果沒有特殊目的,基本上 06/17 21:32
2F:→ OnlyRD: 都屬於設計有問 06/17 21:32
3F:→ OnlyRD: 題的程式,不僅維護困難,容易造成問題,語意也不 06/17 21:32
4F:→ OnlyRD: 清楚。有些程式 06/17 21:32
5F:→ OnlyRD: 為了效能問題,會採用特殊的手法,但是這段程式看 06/17 21:32
6F:→ OnlyRD: 起來效能更差, 06/17 21:32
7F:→ OnlyRD: 記憶體也沒省。 06/17 21:32
8F:推 CoNsTaR: 樓上,說實話這真的還好,它當然不是什麼設計多好的程式 06/17 22:32
9F:→ CoNsTaR: ,但真的還算是清楚易懂,很多比這慘十倍以上的程式你還 06/17 22:32
10F:→ CoNsTaR: 不是要捏著小鳥去處理 orz 06/17 22:32
11F:推 OnlyRD: 也是,但我現在做的事情幾乎都是from scratch,架 06/19 03:20
12F:→ OnlyRD: 構跟基底我打的 06/19 03:20
13F:→ OnlyRD: ,當然不想折磨別人。 06/19 03:20
14F:推 wulouise: 猜先有MSG_OBJ後有*_USE 然後有地方沒改*_USE洞被亂補 06/19 08:27







like.gif 您可能會有興趣的文章
icon.png[問題/行為] 貓晚上進房間會不會有憋尿問題
icon.pngRe: [閒聊] 選了錯誤的女孩成為魔法少女 XDDDDDDDDDD
icon.png[正妹] 瑞典 一張
icon.png[心得] EMS高領長版毛衣.墨小樓MC1002
icon.png[分享] 丹龍隔熱紙GE55+33+22
icon.png[問題] 清洗洗衣機
icon.png[尋物] 窗台下的空間
icon.png[閒聊] 双極の女神1 木魔爵
icon.png[售車] 新竹 1997 march 1297cc 白色 四門
icon.png[討論] 能從照片感受到攝影者心情嗎
icon.png[狂賀] 賀賀賀賀 賀!島村卯月!總選舉NO.1
icon.png[難過] 羨慕白皮膚的女生
icon.png閱讀文章
icon.png[黑特]
icon.png[問題] SBK S1安裝於安全帽位置
icon.png[分享] 舊woo100絕版開箱!!
icon.pngRe: [無言] 關於小包衛生紙
icon.png[開箱] E5-2683V3 RX480Strix 快睿C1 簡單測試
icon.png[心得] 蒼の海賊龍 地獄 執行者16PT
icon.png[售車] 1999年Virage iO 1.8EXi
icon.png[心得] 挑戰33 LV10 獅子座pt solo
icon.png[閒聊] 手把手教你不被桶之新手主購教學
icon.png[分享] Civic Type R 量產版官方照無預警流出
icon.png[售車] Golf 4 2.0 銀色 自排
icon.png[出售] Graco提籃汽座(有底座)2000元誠可議
icon.png[問題] 請問補牙材質掉了還能再補嗎?(台中半年內
icon.png[問題] 44th 單曲 生寫竟然都給重複的啊啊!
icon.png[心得] 華南紅卡/icash 核卡
icon.png[問題] 拔牙矯正這樣正常嗎
icon.png[贈送] 老莫高業 初業 102年版
icon.png[情報] 三大行動支付 本季掀戰火
icon.png[寶寶] 博客來Amos水蠟筆5/1特價五折
icon.pngRe: [心得] 新鮮人一些面試分享
icon.png[心得] 蒼の海賊龍 地獄 麒麟25PT
icon.pngRe: [閒聊] (君の名は。雷慎入) 君名二創漫畫翻譯
icon.pngRe: [閒聊] OGN中場影片:失蹤人口局 (英文字幕)
icon.png[問題] 台灣大哥大4G訊號差
icon.png[出售] [全國]全新千尋侘草LED燈, 水草

請輸入看板名稱,例如:Tech_Job站內搜尋

TOP