女人被狂躁到高潮视频免费无遮挡,内射人妻骚骚骚,免费人成小说在线观看网站,九九影院午夜理论片少妇,免费av永久免费网址

當(dāng)前位置:首頁(yè) > 單片機(jī) > C語(yǔ)言與CPP編程
[導(dǎo)讀]CPU對(duì)我們來說既熟悉又陌生,熟悉的是我們知道代碼是被CPU執(zhí)行的,當(dāng)我們的線上服務(wù)出現(xiàn)問題時(shí)可能首先會(huì)查看CPU負(fù)載情況。陌生的是我們并不知道CPU是如何執(zhí)行代碼的,它對(duì)我們的代碼做了什么。本文意在簡(jiǎn)單解釋我們代碼的生命周期,以及代碼是如何在CPU上跑起來的。編譯-讓計(jì)算機(jī)認(rèn)識(shí)...

CPU對(duì)我們來說既熟悉又陌生,熟悉的是我們知道代碼是被CPU執(zhí)行的,當(dāng)我們的線上服務(wù)出現(xiàn)問題時(shí)可能首先會(huì)查看CPU負(fù)載情況。陌生的是我們并不知道CPU是如何執(zhí)行代碼的,它對(duì)我們的代碼做了什么。本文意在簡(jiǎn)單解釋我們代碼的生命周期,以及代碼是如何在CPU上跑起來的。


編譯-讓計(jì)算機(jī)認(rèn)識(shí)我

一個(gè)漂亮 control c 加上一個(gè)漂亮的 control v,啪~,我們愉快的寫下了代碼,當(dāng)代碼被保存后,它就被存在我們磁盤的某個(gè)地方,它可能是像java或者python這些高級(jí)語(yǔ)言寫的,也可能是像c這種古老語(yǔ)言寫的,但是現(xiàn)在它肯定沒法被運(yùn)行,因?yàn)橛?jì)算機(jī)不認(rèn)識(shí)它們,計(jì)算機(jī)只認(rèn)識(shí)0、1這樣的二進(jìn)制,簡(jiǎn)稱機(jī)器碼,那為什么我們不直接寫機(jī)器碼?如果你有這樣的思考,我只能呵呵了,請(qǐng)你幫我翻譯下以下機(jī)器碼:


001010100101001001001
100100101000101010101
很明顯作為高質(zhì)量人類的我們也無法識(shí)別出這段代碼寫的是什么,于是出現(xiàn)類似java這樣的高級(jí)語(yǔ)言,它們給機(jī)器碼穿上了一層外衣,然后交給偉大的程序員來創(chuàng)造未來。

所以反過來我們的代碼需要被替換成機(jī)器碼,這樣才能被計(jì)算機(jī)認(rèn)識(shí),計(jì)算機(jī)才能幫我們干事。這個(gè)轉(zhuǎn)換的過程我們通常叫「編譯」。


#include
int main()
{
printf("Hello World\n");
return 0;
}
這是一段應(yīng)該每個(gè)程序員都寫過的代碼(hello.c),在Linux下,當(dāng)我們使用GCC來編譯Hello World程序時(shí),只需要最簡(jiǎn)單的命令:

gcc hello.c
./hello
# Hello World
看似很簡(jiǎn)單的一行,但是其實(shí)編譯的過程很復(fù)雜,并不是我們想象中的編譯,真實(shí)是分為4個(gè)步驟,分別是預(yù)處理(Prepressing)、編譯(Compliation)、匯編(Assertmbly)和鏈接(Linking)。

  • 預(yù)編譯:這個(gè)過程主要是處理源代碼中以“#”開始的預(yù)編譯指令,比如“#include”、“define”等。
  • 編譯:這個(gè)過程就是把預(yù)處理完的文件進(jìn)行詞法分析、語(yǔ)法分析、語(yǔ)義分析及優(yōu)化后生產(chǎn)成相應(yīng)的匯編代碼,這個(gè)過程是最復(fù)雜的。
  • 匯編:這個(gè)過程就是將匯編代碼轉(zhuǎn)換成機(jī)器碼,也就是上圖的目標(biāo)文件hello.o
  • 鏈接:我們的代碼程序經(jīng)常是由多個(gè)代碼文件組成的,當(dāng)每個(gè)文件都被匯編成“.o”文件時(shí),需要一套機(jī)制將它們「組裝」在一起,這個(gè)過程就叫做鏈接。
  • 好吧,原來編譯是這么回事,通過這一整套的編譯操作,我們代碼終于能執(zhí)行了,我們簡(jiǎn)簡(jiǎn)單單的運(yùn)行

    ./hello.out即可輸出Hello World。等等,這個(gè)簡(jiǎn)簡(jiǎn)單單的過程發(fā)生了什么?

    連接-中轉(zhuǎn)站和高速公路

    ok,ok,通過編譯,我們的程序終于能執(zhí)行了,接下來讓我們站在CPU的視角來看看Hello World是如何被打印出來的。


    首先編譯好的文件是存在磁盤上的,得先加載到內(nèi)存中,這里你可能會(huì)問:為什么CPU不能直接讀取磁盤的程序運(yùn)行而要經(jīng)過內(nèi)存?答案是慢,緩慢的磁盤會(huì)影響我們程序執(zhí)行的速度,因此需要更加快速、離CPU更近的存儲(chǔ),那就是內(nèi)存。


    內(nèi)存是一大塊存儲(chǔ)空間,可以存儲(chǔ)很多數(shù)據(jù)信息,那么如何找到我們要寫的程序呢?答案是地址,其實(shí)每個(gè)字節(jié)在內(nèi)存中都有一個(gè)地址,這樣當(dāng)CPU去內(nèi)存中讀我們的程序時(shí),只需要根據(jù)對(duì)應(yīng)的地址就可以知道我們程序的具體內(nèi)容。


    等等...,這里似乎又有個(gè)問題,CPU是如何與我們的內(nèi)存、磁盤通信的?應(yīng)該有個(gè)媒介之類的吧。沒錯(cuò),這個(gè)媒介就是主板上的總線芯片組,總線好理解,就像高速公路,數(shù)據(jù)信息可以通過這條高速公路傳遞到CPU中,這個(gè)芯片組是個(gè)什么玩意?電腦主板上芯片很多,這里說的主要是南橋芯片和北橋芯片。先來個(gè)解釋:


  • 北橋芯片:北橋負(fù)責(zé)高速設(shè)備和CPU之間的溝通,主要就是CPU和內(nèi)存、顯卡之間的通信,但是隨著技術(shù)的迭代,主板上的北橋芯片已經(jīng)被內(nèi)置到了CPU里了。
  • 南橋芯片:南橋負(fù)責(zé)低速設(shè)備和北橋之間的通信,主要負(fù)責(zé)I/O總線之間的通信,如USB、LAN、ATA、SATA、音頻控制器、鍵盤控制器、實(shí)時(shí)時(shí)鐘控制器、高級(jí)電源管理等。
  • 嗯... 為什么CPU與高速設(shè)備、低速設(shè)備之間的通信需要這兩個(gè)芯片?CPU自己不能干嗎?這里還是類似拆分任務(wù)的功能,如果把所有的任務(wù)都交給CPU來處理,CPU會(huì)太忙了,還有比較重要的一點(diǎn),如果南橋芯片壞了,那么我們可以直接更換南橋,而不用換掉整個(gè)CPU。


    終于CPU通過總線和芯片打通了磁盤、內(nèi)存之間的通信了,接下來的一切開始交給CPU。


    CPU-最強(qiáng)大腦

    CPU全稱是Central Processing Unit,即中央處理單元,它的本質(zhì)就是一塊超大規(guī)模的集成電路。從邏輯上來分,它的內(nèi)部是由寄存器、控制器、運(yùn)算器和時(shí)鐘組成的,下面來解釋下各個(gè)組成是干什么的。


    • 寄存器:CPU內(nèi)部其實(shí)有很多類型的寄存器,我們只需了解寄存器就是暫存數(shù)據(jù)、指令等信息的,它的本質(zhì)是臨時(shí)存儲(chǔ),由于是直接集成在CPU內(nèi)部,所以讀寫它們的速度很快,一般一個(gè)CPU內(nèi)部會(huì)有20-100個(gè)寄存器,這里給大家列舉下常用寄存器與其功能。


    • 累加寄存器:存儲(chǔ)執(zhí)行運(yùn)算的數(shù)據(jù)和運(yùn)算后的數(shù)據(jù)
    • 標(biāo)志寄存器:存儲(chǔ)運(yùn)算處理后的CPU的狀態(tài)
    • 程序計(jì)數(shù)器:存儲(chǔ)下一條指令所在內(nèi)存的地址
    • 基址寄存器:存儲(chǔ)數(shù)據(jù)內(nèi)存的起始地址
    • 變址寄存器:存儲(chǔ)基址寄存器的相對(duì)地址
    • 通用寄存器:存儲(chǔ)任意數(shù)據(jù)
    • 指令寄存器:存儲(chǔ)指令,CPU內(nèi)部使用,程序員無法通過程序?qū)υ摷拇嫫鬟M(jìn)行讀寫操作
    • 棧寄存器:存儲(chǔ)棧區(qū)域的起始地址
    • 控制器:控制器負(fù)責(zé)把數(shù)據(jù)讀出或者寫入寄存器,并根據(jù)指令的結(jié)果來控制計(jì)算機(jī)。


    • 運(yùn)算器:從名字就可以猜出來,運(yùn)算器的主要工作就是運(yùn)算,運(yùn)算從內(nèi)存讀入寄存器的值


    • 時(shí)鐘:它并不是我們見的鐘表概念,它代表了你的CPU的工作頻率,頻率越高說明你的CPU處理的速度越快,但是越快就會(huì)帶來另一個(gè)問題:散熱。


    綜上所述,CPU的大致工作流程如下:在時(shí)鐘信號(hào)到來的時(shí)候,就開始工作,通過控制器把內(nèi)存的數(shù)據(jù)讀到各個(gè)寄存器中,然后如果有計(jì)算相關(guān)的邏輯,就交給運(yùn)算器。發(fā)現(xiàn)沒有,CPU的工作其實(shí)挺簡(jiǎn)單的,本質(zhì)就是不停的讀指令、執(zhí)行指令。但是CPU是如何讀到我們的代碼指令的,以及我們的代碼里面的if else、函數(shù)調(diào)用都是如何執(zhí)行分支判斷、函數(shù)跳轉(zhuǎn)的,我們來看個(gè)例子:


    a = 1 #0x0010
    b = 2 #0x0011
    if a > b { #0x0012
    printf("%s","a") #0x0013
    } else {
    add(a,b) #0x0014
    }
    printf("%s","end") #0x0017

    func add(int a,int b) { #0x0020
    return a b
    }
    這是段非常簡(jiǎn)單的偽代碼,有分支判斷、有函數(shù)跳轉(zhuǎn)。我們來從CPU的角度看看它是如何執(zhí)行的:

  • 首先每段程序都有個(gè)開始的地址0x0010,也就是CPU讀取程序的入口
  • 把a(bǔ)=1這個(gè)數(shù)字讀入通用寄存器中,程序計(jì)數(shù)器(PC寄存器)自動(dòng)加1,即指向下一條指令 0x0011
  • 指令寄存器拿到程序計(jì)數(shù)器的指令地址,把b=2這個(gè)數(shù)字讀入通用寄存器中,程序計(jì)數(shù)器(PC寄存器)自動(dòng)加1,即指向下一條指令0x0012
  • 指令寄存器發(fā)現(xiàn)此處是比較邏輯,會(huì)執(zhí)行a-b,此時(shí)可能會(huì)有三個(gè)結(jié)果分別是大于0,等于0,小于0,然后把這個(gè)結(jié)果存到標(biāo)志寄存器里,這里有個(gè)小知識(shí),我們經(jīng)常說的是CPU是64位或者32位,其實(shí)也表示了標(biāo)志寄存器的長(zhǎng)度
  • 很明顯,a是小于b的,CPU根據(jù)標(biāo)志寄存器的狀態(tài)值應(yīng)該跳轉(zhuǎn)到else里面,注意這時(shí)程序計(jì)數(shù)器的值不是加1,而是設(shè)置成else的地址 0x0014,當(dāng)執(zhí)行到0x0015的時(shí)候,需要發(fā)生函數(shù)跳轉(zhuǎn),程序計(jì)數(shù)器會(huì)被設(shè)置成 0x0020,但是這里并不是簡(jiǎn)單的函數(shù)跳轉(zhuǎn)(專業(yè)術(shù)語(yǔ)叫做call),因?yàn)樵诤瘮?shù)執(zhí)行完畢之后,還要返回,也就是程序計(jì)數(shù)器需要從0x0020再變成0x0017。call執(zhí)行的時(shí)候會(huì)把后續(xù)要執(zhí)行的指令地址0x0017存到中。
  • 當(dāng)我們的add函數(shù)執(zhí)行完畢之后,會(huì)有個(gè)return,return的時(shí)候會(huì)把上一步驟存入棧中的地址0x0017寫入程序計(jì)數(shù)器中
  • 指令寄存器根據(jù)程序計(jì)數(shù)器當(dāng)前的地址執(zhí)行最后的打?。╡nd),結(jié)束。
  • 順序執(zhí)行的指令代碼,程序計(jì)數(shù)器會(huì)自動(dòng)累加(當(dāng)然不一定累加的是1),然后找到下一條要執(zhí)行的指令。


    分支判斷的時(shí)候,程序計(jì)數(shù)器不是簡(jiǎn)單的累加地址,需要地址的跳轉(zhuǎn)。


    函數(shù)調(diào)用不僅僅需要跳轉(zhuǎn)地址,還要把函數(shù)執(zhí)行完畢之后要執(zhí)行的地址存下來,方便折回繼續(xù)執(zhí)行。


    其實(shí)還有個(gè)循環(huán)執(zhí)行,也就是我們代碼中的for、while之類的,這時(shí)程序計(jì)數(shù)器會(huì)不停的在某些地址之間來回切換。



    本站聲明: 本文章由作者或相關(guān)機(jī)構(gòu)授權(quán)發(fā)布,目的在于傳遞更多信息,并不代表本站贊同其觀點(diǎn),本站亦不保證或承諾內(nèi)容真實(shí)性等。需要轉(zhuǎn)載請(qǐng)聯(lián)系該專欄作者,如若文章內(nèi)容侵犯您的權(quán)益,請(qǐng)及時(shí)聯(lián)系本站刪除。
    換一批
    延伸閱讀

    8位單片機(jī)在嵌入式設(shè)計(jì)領(lǐng)域已經(jīng)成為半個(gè)多世紀(jì)以來的主流選擇。盡管嵌入式系統(tǒng)市場(chǎng)日益復(fù)雜,8位單片機(jī)依然不斷發(fā)展,積極應(yīng)對(duì)新的挑戰(zhàn)和系統(tǒng)需求。如今,Microchip推出的8位PIC?和AVR?單片機(jī)系列,配備了先進(jìn)的獨(dú)立...

    關(guān)鍵字: 單片機(jī) 嵌入式 CPU

    阿聯(lián)酋迪拜2025年8月26日 /美通社/ -- 納斯達(dá)克上市公司Robo.ai Inc.今日正式宣布完成品牌煥新升級(jí),并于8月26日正式啟用全新納斯達(dá)克股票代碼"...

    關(guān)鍵字: AI 人工智能 代碼 智能科技

    北京2025年8月13日 /美通社/ -- 近日,北京積算科技有限公司(以下簡(jiǎn)稱"積算科技")推出一站式AlphaFold3在線算力服務(wù),現(xiàn)已開放免費(fèi)使用。其內(nèi)置優(yōu)化后的AlphaFold3模型,支持...

    關(guān)鍵字: ALPHA 代碼 圖形化 蛋白質(zhì)

    上海2025年8月15日 /美通社/ -- 在數(shù)字化轉(zhuǎn)型浪潮與數(shù)據(jù)安全需求的雙重驅(qū)動(dòng)下,瀾起科技今日重磅推出第六代津逮? 性能核 CPU (以下簡(jiǎn)稱 C6P )。這款融合突破性架構(gòu)、全棧兼容性與芯片級(jí)安全防護(hù)的高性能服...

    關(guān)鍵字: CPU BSP 數(shù)字化 AI

    采用分離式架構(gòu),充分利用主機(jī) CPU 和 PCIe? 基礎(chǔ)設(shè)施,克服傳統(tǒng)存儲(chǔ)瓶頸

    關(guān)鍵字: CPU 數(shù)據(jù)中心 服務(wù)器

    受生成式 AI 驅(qū)動(dòng), RISC-V 芯片市場(chǎng)快速發(fā)展。預(yù)計(jì)到2030年,RISC-V SoC出貨量將達(dá)到1618.1億顆,營(yíng)收將達(dá)到927億美元。其中,用于AI加速器的RISC-V SoC出貨量將達(dá)到41億顆,營(yíng)收將達(dá)...

    關(guān)鍵字: RISC-V CPU AI CUDA ARM 推理

    北京2025年7月21日 /美通社/ -- 浪潮信息宣布元腦企智一體機(jī)已率先完成對(duì)Kimi K2 萬(wàn)億參數(shù)大模型的適配支持,并實(shí)現(xiàn)單用戶70 tokens/s的流暢輸出速度,為企業(yè)客戶高效部署應(yīng)用大模型提供高處...

    關(guān)鍵字: 模型 AGENT TOKEN 代碼

    7月21日消息,“全球最佳游戲CPU”銳龍7 9800X3D自去年11月上市以來,價(jià)格一直比較堅(jiān)挺,前期還經(jīng)常處于缺貨狀態(tài)。

    關(guān)鍵字: CPU GPU

    人工智能 (AI) 正在以驚人的速度發(fā)展。企業(yè)不再僅僅是探索 AI,而是積極推動(dòng) AI 的規(guī)模化落地,從實(shí)驗(yàn)性應(yīng)用轉(zhuǎn)向?qū)嶋H部署。隨著生成式模型日益精簡(jiǎn)和高效,AI 的重心正從云端轉(zhuǎn)向邊緣側(cè)。如今,人們不再質(zhì)疑邊緣 AI...

    關(guān)鍵字: 人工智能 CPU GPU

    CPU通過將代碼轉(zhuǎn)換為機(jī)器語(yǔ)言、通過指令集架構(gòu)(ISA)識(shí)別代碼、以及利用控制單元(CU)和算術(shù)邏輯單元(ALU)執(zhí)行代碼這三種主要方式來認(rèn)識(shí)代碼。CPU首先將編寫的高級(jí)語(yǔ)言代碼通過編譯器轉(zhuǎn)換為低級(jí)語(yǔ)言,即機(jī)器語(yǔ)言,這是...

    關(guān)鍵字: CPU 機(jī)器語(yǔ)言
    關(guān)閉