日B视频 亚洲,啪啪啪网站一区二区,91色情精品久久,日日噜狠狠色综合久,超碰人妻少妇97在线,999青青视频,亚洲一区二卡,让本一区二区视频,日韩网站推荐

0
  • 聊天消息
  • 系統(tǒng)消息
  • 評論與回復(fù)
登錄后你可以
  • 下載海量資料
  • 學(xué)習(xí)在線課程
  • 觀看技術(shù)視頻
  • 寫文章/發(fā)帖/加入社區(qū)
會員中心
創(chuàng)作中心

完善資料讓更多小伙伴認(rèn)識你,還能領(lǐng)取20積分哦,立即完善>

3天內(nèi)不再提示

page struct的三種存放方式

Linux閱碼場 ? 來源:Linuxer ? 2020-08-03 16:33 ? 次閱讀
加入交流群
微信小助手二維碼

掃碼添加小助手

加入工程師交流群

隨著硬件能力的提升,系統(tǒng)內(nèi)存容量變得越來越大。尤其是在服務(wù)器上,過T級別的內(nèi)存容量也已經(jīng)不罕見了。

如此海量內(nèi)存給內(nèi)核帶來了很多挑戰(zhàn),其中之一就是page struct存放在哪里。

page struct的三種存放方式

在內(nèi)核中,我們將物理內(nèi)存按照頁大小進行管理。這樣每個頁就對應(yīng)一個page struct作為這個頁的管理數(shù)據(jù)結(jié)構(gòu)。

隨著內(nèi)存容量的增加,相對應(yīng)的page struct也就增加。而這部分內(nèi)存和其他的內(nèi)存略有不同,因為這部分內(nèi)存不能給到頁分配器。也就是必須在系統(tǒng)能夠正常運行起來之前就分配好。

在內(nèi)核中我們可以看到,為了應(yīng)對這樣的變化進化出了幾個不同的版本。有幸的是,這部分內(nèi)容我們現(xiàn)在還能在代碼中直接看到,因為這個實現(xiàn)是通過內(nèi)核配置來區(qū)分的。我們通過查找_pfn_to_page的定義就能發(fā)現(xiàn)一下幾種memory model:

CONFIG_FLATMEM

CONFIG_SPARSEMEM

CONFIGSPARSEMEMVMEMMAP

接下來讓小編給各位看官一一道來。

1) FLATMEM

在這種情況下,宏_pfn_to_page的定義是:

#define__pfn_to_page(pfn)(mem_map+((pfn)-ARCH_PFN_OFFSET))

而這個mem_map的定義是

structpage*mem_map;

所以在這種情況下,page struct就是一個大數(shù)組,所有的人都按照自己的物理地址有序得挨著。

2) SPARSEMEM

雖然第一種方式非常簡單直觀,但是有幾個非常大的缺點:

內(nèi)存如果有空洞,那么中間可能會有巨大的page struct空間浪費

所有的page struct內(nèi)存都在一個NUMA節(jié)點上,會耗盡某一個節(jié)點內(nèi)存,甚至是分配失敗

且會產(chǎn)生夸NUMA訪問導(dǎo)致性能下降

所以第二種方式就是將內(nèi)存按照一定粒度,如128M,劃分了section,每個section中有個成員指定了對應(yīng)的page struct的存儲空間。

這樣就解決了上述的幾個問題:

如果有空洞,那么對應(yīng)的 page struct就不會占用空間

每個section對應(yīng)的page struct是屬于本地NUMA的

怎么樣,是不是覺得很完美。這一部分具體的實現(xiàn)可以可以看函數(shù)sparse_init()函數(shù)。

有了這個基礎(chǔ)知識,我們再來看這種情況下_pfn_to_page的定義:

#define __pfn_to_page(pfn) ({ unsigned long __pfn = (pfn); struct mem_section *__sec = __pfn_to_section(__pfn); __section_mem_map_addr(__sec) + __pfn; })

就是先找到pfn對應(yīng)的section,然后在section中保存的地址上翻譯出對應(yīng)pfn的page struct。

既然講到了這里,我們就要對sparsemem中重要的組成部分mem_section多說兩句。

先來一張mem_section的整體圖解:

這是一個 NRSECTIONROOTS x SECTIONSPERROOT的二維數(shù)組。其中每一個成員就代表了我們剛才提到的128M內(nèi)存。

當(dāng)然最開始它不是這個樣子的。

其實最開始這個數(shù)組是一個靜態(tài)數(shù)組。很明顯這么做帶來的問題是這個數(shù)組定義太大太小都不合適。所以后來引進了CONFIGSPARSEMEMEXTREME編譯選項,當(dāng)設(shè)置為y時,這個數(shù)組就變成了動態(tài)的。

如果上面這個算作是空間上的限制的話,那么接下來就是一個時間上的限制了。

在系統(tǒng)初始化時,每個mem_section都要和相應(yīng)的內(nèi)存空間關(guān)聯(lián)。在老版本上,這個步驟通過對整個數(shù)組接待完成。原來的版本上問題不大,因為整個數(shù)組的大小還沒有很大。但隨著內(nèi)存容量的增加,這個數(shù)值就變得對系統(tǒng)有影響了。如果系統(tǒng)上確實有這么多內(nèi)存,那么確實需要初始化也就忍了。但是在內(nèi)存較小的系統(tǒng)上,哪怕沒有這么多內(nèi)存,還是要挨個初始化,那就浪費了太多的時間。

commit c4e1be9ec1130fff4d691cdc0e0f9d666009f9aeAuthor: Dave Hansen Date: Thu Jul 6 15:36:44 2017 -0700 mm, sparsemem: break out of loops earl

Dave在這個提交中增加了對系統(tǒng)最大存在內(nèi)存的跟蹤,來減少不必要的初始化時間。

瞧,內(nèi)核代碼一開始其實也沒有這么高大上不是。

3) SPARSEMEM_VMEMMAP

最后要講的,也是當(dāng)前x86系統(tǒng)默認(rèn)配置的內(nèi)存模型是SPARSEMEM_VMEMMAP。那為什么要引入這么一個新的模型呢?那自然是sparsemem依然有不足。

細(xì)心的朋友可能已經(jīng)注意到了,前兩種內(nèi)存模型在做pfn到page struct轉(zhuǎn)換是有著一些些的差異。為了看得清,我們把這兩個定義再拿過來對比一下:

先看看FLATMEM時的定義:

#define__pfn_to_page(pfn)(mem_map+((pfn)-ARCH_PFN_OFFSET))

再來看看使用SPASEMEM后的定義:

#define __pfn_to_page(pfn) ({ unsigned long __pfn = (pfn); struct mem_section *__sec = __pfn_to_section(__pfn); __section_mem_map_addr(__sec) + __pfn; })

更改后,需要先找到section,然后再從section->memmap的內(nèi)容中換算出page的地址。

不僅計算的內(nèi)容多了,更重要的是還有一次訪問內(nèi)存的操作

可以想象,訪問內(nèi)存和單純計算之間的速度差異那是巨大的差距。

既然產(chǎn)生了這樣的問題,那有沒有辦法解決呢?其實說來簡單,內(nèi)核開發(fā)者利用了我們常見的一個內(nèi)存單元來解決這個問題。

頁表

是不是很簡單粗暴?如果我們能夠通過某種方式將page struct線性映射到頁表,這樣我們不就能又通過簡單的計算來換算物理地址和page struct了么?

內(nèi)核開發(fā)者就是這么做的,我們先來看一眼最后那簡潔的代碼:

#define__pfn_to_page(pfn)(vmemmap+(pfn))

經(jīng)過內(nèi)核開發(fā)這的努力,物理地址到page struct的轉(zhuǎn)換又變成如此的簡潔。不需要訪問內(nèi)存,所以速度的問題得到了解決。

但是天下沒有免費的午餐,世界哪有這么美好,魚和熊掌可以兼得的情況或許只有在夢境之中。為了達到如此簡潔的轉(zhuǎn)化,我們是要付出代價的。為了實現(xiàn)速度上的提升,我們付出了空間的代價。

至此引出了計算機界一個經(jīng)典的話題:

時間和空間的轉(zhuǎn)換

話不多說,也不矯情了,我們來看看內(nèi)核中實現(xiàn)的流程。

既然是利用了頁表進行轉(zhuǎn)換,那么自然是要構(gòu)建頁表在做這樣的映射。這個步驟主要由函數(shù)vmemmap_populate()來完成,其中還區(qū)分了有沒有大頁的情況。我們以普通頁的映射為例,看看這個實現(xiàn)。

int __meminit vmemmap_populate_basepages(unsigned long start, unsigned long end, int node){ unsigned long addr = start; pgd_t *pgd; p4d_t *p4d; pud_t *pud; pmd_t *pmd; pte_t *pte; for (; addr < end; addr += PAGE_SIZE) { pgd = vmemmap_pgd_populate(addr, node); if (!pgd) return -ENOMEM; p4d = vmemmap_p4d_populate(pgd, addr, node); if (!p4d) return -ENOMEM; pud = vmemmap_pud_populate(p4d, addr, node); if (!pud) return -ENOMEM; pmd = vmemmap_pmd_populate(pud, addr, node); if (!pmd) return -ENOMEM; pte = vmemmap_pte_populate(pmd, addr, node); if (!pte) return -ENOMEM; vmemmap_verify(pte, node, addr, addr + PAGE_SIZE); } return 0;}

內(nèi)核代碼的優(yōu)美之處就在于,你可能不一定看懂了所有細(xì)節(jié),但是從優(yōu)美的結(jié)構(gòu)上能猜到究竟做了些什么。上面這段代碼的工作就是對每一個頁,按照層級去填充頁表內(nèi)容。其中具體的細(xì)節(jié)就不在這里展開了,相信有興趣的同學(xué)會自行去探索。

那這么做的代價究竟是多少呢?

以x86為例,每個section是128M,那么每個section的page struct正好是2M,也就是一個大頁。

(128M / 4K) * 64 = (128 * (1 < 20) / (1 < 12)) * 64 = 2M

假如使用大頁做頁表映射,那么每64G才用掉一個4K頁表做映射。

128M * 512 = 64G

所以在使用大頁映射的情況下,這個損耗的級別在百萬分之一。還是能夠容忍的。

好了,我們終于沿著內(nèi)核發(fā)展的歷史重走了一遍安放page struct之路。相信大家在這一路上領(lǐng)略了代碼演進的樂趣,也會對以后自己代碼的設(shè)計有了更深的思考。

聲明:本文內(nèi)容及配圖由入駐作者撰寫或者入駐合作網(wǎng)站授權(quán)轉(zhuǎn)載。文章觀點僅代表作者本人,不代表電子發(fā)燒友網(wǎng)立場。文章及其配圖僅供工程師學(xué)習(xí)之用,如有內(nèi)容侵權(quán)或者其他違規(guī)問題,請聯(lián)系本站處理。 舉報投訴
  • 服務(wù)器
    +關(guān)注

    關(guān)注

    14

    文章

    10371

    瀏覽量

    91768
  • 數(shù)據(jù)結(jié)構(gòu)

    關(guān)注

    3

    文章

    573

    瀏覽量

    41691
  • PAGE
    +關(guān)注

    關(guān)注

    0

    文章

    11

    瀏覽量

    20582

原文標(biāo)題:page結(jié)構(gòu)體,何處安放你的靈魂?

文章出處:【微信號:LinuxDev,微信公眾號:Linux閱碼場】歡迎添加關(guān)注!文章轉(zhuǎn)載請注明出處。

收藏 人收藏
加入交流群
微信小助手二維碼

掃碼添加小助手

加入工程師交流群

    評論

    相關(guān)推薦
    熱點推薦

    HINET工業(yè)智能網(wǎng)關(guān)三種聯(lián)網(wǎng)方式操作指南

    智能網(wǎng)關(guān)支持三種聯(lián)網(wǎng)方式:有線連接、移動網(wǎng)絡(luò)、無線連接。三種聯(lián)網(wǎng)方式可分別適用于不同的網(wǎng)絡(luò)環(huán)境?,F(xiàn)場具備有線網(wǎng)絡(luò)條件時,建議優(yōu)先選用有線連接方式
    的頭像 發(fā)表于 04-23 17:12 ?420次閱讀
    HINET工業(yè)智能網(wǎng)關(guān)<b class='flag-5'>三種</b>聯(lián)網(wǎng)<b class='flag-5'>方式</b>操作指南

    ATE系統(tǒng)中這三種測量卡的架構(gòu)和功能

    測試儀行業(yè)面臨的一個挑戰(zhàn)是,如何在不顯著增加測試儀時間、尺寸或成本的情況下,滿足對大量測試通道的需求。盡管半導(dǎo)體測試儀(也稱為自動測試器件(ATE))種類繁多,但在大多數(shù)測試儀都包含三種主要卡:電壓
    的頭像 發(fā)表于 04-09 15:12 ?178次閱讀
    ATE系統(tǒng)中這<b class='flag-5'>三種</b>測量卡的架構(gòu)和功能

    AI技術(shù)時代三種全新工作模式如何實現(xiàn)

    AI技術(shù)正在重塑我們的工作。前沿企業(yè)以“人類主導(dǎo)、智能體運營”為核心,形成三種AI技術(shù)的融合模式:人類+AI技術(shù)助手、人機混合、人類主導(dǎo)智能體運營,這些模式不僅提升效率,更在重構(gòu)協(xié)作方式,幫助組織以更低的阻力邁向成功。
    的頭像 發(fā)表于 01-29 15:08 ?779次閱讀

    C語言中實現(xiàn)函數(shù)宏的三種方式

    在宏的第一個分號后便結(jié)束。即 a = b 和 b = tmp 均不受控制語句所作用。 因此,在工程中,一般使用三種方式來對函數(shù)宏進行封裝,分別為 {}、do{...}while(0
    發(fā)表于 12-29 07:34

    請問CW32芯片的三種工作模式是什么?

    CW32芯片的三種工作模式是什么?
    發(fā)表于 12-26 06:48

    宜科電子推出三種不同原理標(biāo)簽傳感器

    在工業(yè)自動化與智能包裝領(lǐng)域,標(biāo)簽檢測的精度、速度與適應(yīng)性直接決定了生產(chǎn)線的效率與產(chǎn)品合規(guī)性。針對不同材質(zhì)標(biāo)簽(如紙質(zhì)、薄膜、金屬箔)及復(fù)雜檢測環(huán)境,我們推出超聲波、光電、電容三種不同原理標(biāo)簽傳感器,以多模融合、精準(zhǔn)識別、智能適應(yīng)為核心,為食品包裝、醫(yī)藥制造、物流分揀等行業(yè)提供全場景解決方案。
    的頭像 發(fā)表于 11-08 15:07 ?2118次閱讀

    伺服電機的三種制動方式有什么區(qū)別?

    伺服電機作為自動化控制系統(tǒng)中執(zhí)行元件的核心部件,其制動性能直接影響設(shè)備的定位精度和安全可靠性。目前主流的伺服電機制動方式包括動態(tài)制動、再生制動和電磁機械制動三種,它們在制動原理、應(yīng)用場景及技術(shù)特點上
    的頭像 發(fā)表于 09-19 18:26 ?2271次閱讀
    伺服電機的<b class='flag-5'>三種</b>制動<b class='flag-5'>方式</b>有什么區(qū)別?

    TC377配置SMU FSP時,如何配置頻率參數(shù);三種模式有何區(qū)別,配置上有何區(qū)別?

    TC377配置SMU FSP時,如何配置頻率參數(shù);三種模式有何區(qū)別,配置上有何區(qū)別?
    發(fā)表于 08-08 07:48

    三種SPWM波形生成算法的分析與實現(xiàn)

    摘要:變頻技術(shù)作為現(xiàn)代電力電子的核心技術(shù),集現(xiàn)代電子、信息和智能技術(shù)于一體。而SPW(正弦波脈寬調(diào)制)波的產(chǎn)生和控制則是變頻技術(shù)的核心之一。本文對SPI波形生成的三種算法-對稱規(guī)則采樣法、不對稱規(guī)則
    發(fā)表于 07-31 13:34

    CAN總線電容過大?三種解決方案來了

    在新能源汽車路試中,CAN總線傳輸異常是一個常見問題。本期我們將探討由于總線電容過大導(dǎo)致的下降沿過緩問題,并介紹三種有效的解決方案。CAN總線下降沿過緩問題新能源路試工程師在分析CAN總線波形
    的頭像 發(fā)表于 07-22 11:36 ?886次閱讀
    CAN總線電容過大?<b class='flag-5'>三種</b>解決方案來了

    MEMS中的三種測溫方式

    在集成MEMS芯片的環(huán)境溫度測量領(lǐng)域,熱阻、熱電堆和PN結(jié)原理是三種主流技術(shù)。熱阻是利用熱敏電阻,如金屬鉑或注入硅的溫度電阻系數(shù)恒定,即電阻隨溫度線性變化的特性測溫,電阻變化直接對應(yīng)絕對溫度,需恒流源供電。
    的頭像 發(fā)表于 07-16 13:58 ?1938次閱讀
    MEMS中的<b class='flag-5'>三種</b>測溫<b class='flag-5'>方式</b>

    1553B總線常見三種組網(wǎng)方式

    1553B總線作為航空電子系統(tǒng)中的關(guān)鍵通信協(xié)議,其組網(wǎng)方式直接影響系統(tǒng)的可靠性和實時性。本文將深入解析1553B總線的三種典型組網(wǎng)結(jié)構(gòu):單總線結(jié)構(gòu)、雙冗余總線和多總線分層架構(gòu),并結(jié)合實際應(yīng)用場景分析
    的頭像 發(fā)表于 06-21 17:39 ?2483次閱讀
    1553B總線常見<b class='flag-5'>三種</b>組網(wǎng)<b class='flag-5'>方式</b>

    開關(guān)電源三種控制模式:PWM/PFM/PSM

    摘要 本文詳細(xì)介紹了開關(guān)電源的三種主要調(diào)制方式:PWM(脈沖寬度調(diào)制)、PFM(脈沖頻率調(diào)制)和PSM(脈沖跨周期調(diào)制)。PWM通過調(diào)整脈沖寬度保持恒定頻率,適用于重負(fù)載,但輕負(fù)載效率低。PFM則在
    發(fā)表于 06-09 16:11

    HarmonyOS基礎(chǔ)組件:Button三種類型的使用

    中的Button相較于Android原生來說,功能比較豐富,擴展性高,減少了開發(fā)者的代碼數(shù)量,簡化了使用方式。不僅可以自定義圓角還支持三種樣式。 常用屬性 名稱 參數(shù)類型 描述 type
    的頭像 發(fā)表于 06-09 15:48 ?2724次閱讀
    HarmonyOS基礎(chǔ)組件:Button<b class='flag-5'>三種</b>類型的使用

    介紹三種常見的MySQL高可用方案

    在生產(chǎn)環(huán)境中,為了確保數(shù)據(jù)庫系統(tǒng)的連續(xù)可用性、降低故障恢復(fù)時間以及實現(xiàn)業(yè)務(wù)的無縫切換,高可用(High Availability, HA)方案至關(guān)重要。本文將詳細(xì)介紹三種常見的 MySQL 高可用
    的頭像 發(fā)表于 05-28 17:16 ?1453次閱讀
    温宿县| 左贡县| 大英县| 沂源县| 巴青县| 绍兴市| 阿拉尔市| 五莲县| 双流县| 宿松县| 临夏县| 婺源县| 交口县| 丹寨县| 武邑县| 金阳县| 双鸭山市| 哈密市| 社旗县| 吉安县| 平度市| 左权县| 黑河市| 信阳市| 永年县| 会同县| 长寿区| 荔浦县| 蚌埠市| 房产| 城市| 宁海县| 宁蒗| 邯郸市| 新建县| 平舆县| 香港 | 砚山县| 兴城市| 大同县| 洪雅县|