日本黄色一级经典视频|伊人久久精品视频|亚洲黄色色周成人视频九九九|av免费网址黄色小短片|黄色Av无码亚洲成年人|亚洲1区2区3区无码|真人黄片免费观看|无码一级小说欧美日免费三级|日韩中文字幕91在线看|精品久久久无码中文字幕边打电话

當(dāng)前位置:首頁 > 嵌入式 > 嵌入式教程
[導(dǎo)讀]可以說,共享內(nèi)存是一種最為高效的進程間通信方式。因為進程可以直接讀寫內(nèi)存,不需要任何數(shù)據(jù)的復(fù)制。為了在多個進程間交換信息,內(nèi)核專門留出了一塊內(nèi)存區(qū)。這段內(nèi)存區(qū)可以由需要訪問的進程將其映射到自己的私有地址空間。因此,進程就可以直接讀寫這一內(nèi)存區(qū)而不需要進行數(shù)據(jù)的復(fù)制,從而大大提高了效率。

8.5共享內(nèi)存8.5.1共享內(nèi)存概述

可以說,共享內(nèi)存是一種最為高效的進程間通信方式。因為進程可以直接讀寫內(nèi)存,不需要任何數(shù)據(jù)的復(fù)制。為了在多個進程間交換信息,內(nèi)核專門留出了一塊內(nèi)存區(qū)。這段內(nèi)存區(qū)可以由需要訪問的進程將其映射到自己的私有地址空間。因此,進程就可以直接讀寫這一內(nèi)存區(qū)而不需要進行數(shù)據(jù)的復(fù)制,從而大大提高了效率。當(dāng)然,由于多個進程共享一段內(nèi)存,因此也需要依靠某種同步機制,如互斥鎖和信號量等(請參考本章的共享內(nèi)存實驗)。其原理示意圖如圖8.8所示。

圖8.8共享內(nèi)存原理示意圖

8.5.2共享內(nèi)存的應(yīng)用1.函數(shù)說明

共享內(nèi)存的實現(xiàn)分為兩個步驟,第一步是創(chuàng)建共享內(nèi)存,這里用到的函數(shù)是shmget(),也就是從內(nèi)存中獲得一段共享內(nèi)存區(qū)域,第二步映射共享內(nèi)存,也就是把這段創(chuàng)建的共享內(nèi)存映射到具體的進程空間中,這里使用的函數(shù)是shmat()。到這里,就可以使用這段共享內(nèi)存了,也就是可以使用不帶緩沖的I/O讀寫命令對其進行操作。除此之外,當(dāng)然還有撤銷映射的操作,其函數(shù)為shmdt()。這里就主要介紹這3個函數(shù)。

2.函數(shù)格式

表8.20列舉了shmget()函數(shù)的語法要點。

表8.20 shmget()函數(shù)語法要點

所需頭文件

#include<sys/types.h>
#include<sys/ipc.h>
#include<sys/shm.h>

函數(shù)原型

intshmget(key_tkey,intsize,intshmflg)

函數(shù)傳入值

key:共享內(nèi)存的鍵值,多個進程可以通過它訪問同一個共享內(nèi)存,其中有個特殊值IPC_PRIVATE。它用于創(chuàng)建當(dāng)前進程的私有共享內(nèi)存

size:共享內(nèi)存區(qū)大小

shmflg:同open()函數(shù)的權(quán)限位,也可以用八進制表示法

函數(shù)返回值

成功:共享內(nèi)存段標(biāo)識符

出錯:-1

表8.21列舉了shmat()函數(shù)的語法要點。

表8.21 shmat()函數(shù)語法要點

所需頭文件

#include<sys/types.h>
#include<sys/ipc.h>
#include<sys/shm.h>

函數(shù)原型

char*shmat(intshmid,constvoid*shmaddr,intshmflg)

函數(shù)傳入值

shmid:要映射的共享內(nèi)存區(qū)標(biāo)識符

shmaddr:將共享內(nèi)存映射到指定地址(若為0則表示系統(tǒng)自動分配地址并把該段共享內(nèi)存映射到調(diào)用進程的地址空間)

shmflg

SHM_RDONLY:共享內(nèi)存只讀

默認(rèn)0:共享內(nèi)存可讀寫

函數(shù)返回值

成功:被映射的段地址

出錯:-1

表8.22列舉了shmdt()函數(shù)的語法要點。

表8.22 shmdt()函數(shù)語法要點

所需頭文件

#include<sys/types.h>
#include<sys/ipc.h>
#include<sys/shm.h>

函數(shù)原型

intshmdt(constvoid*shmaddr)

函數(shù)傳入值

shmaddr:被映射的共享內(nèi)存段地址

函數(shù)返回值

成功:0

出錯:-1

3.使用實例

該實例說明如何使用基本的共享內(nèi)存函數(shù)。首先是創(chuàng)建一個共享內(nèi)存區(qū)(采用的共享內(nèi)存的鍵值為IPC_PRIVATE,是因為本實例中創(chuàng)建的共享內(nèi)存是父子進程之間的共用部分),之后創(chuàng)建子進程,在父子兩個進程中將共享內(nèi)存分別映射到各自的進程地址空間之中。

父進程先等待用戶輸入,然后將用戶輸入的字符串寫入到共享內(nèi)存,之后往共享內(nèi)存的頭部寫入“WROTE”字符串表示父進程已成功寫入數(shù)據(jù)。子進程一直等到共享內(nèi)存的頭部字符串為“WROTE”,然后將共享內(nèi)存的有效數(shù)據(jù)(在父進程中用戶輸入的字符串)在屏幕上打印。父子兩個進程在完成以上工作之后,分別解除與共享內(nèi)存的映射關(guān)系。

最后在子進程中刪除共享內(nèi)存。因為共享內(nèi)存自身并不提供同步機制,所以應(yīng)該額外實現(xiàn)不同進程之間的同步(例如:信號量)。為了簡單起見,在本實例中用標(biāo)志字符串來實現(xiàn)非常簡單的父子進程之間的同步。

這里要介紹的一個命令是ipcs,這是用于報告進程間通信機制狀態(tài)的命令。它可以查看共享內(nèi)存、消息隊列等各種進程間通信機制的情況,這里使用了system()函數(shù)用于調(diào)用shell命令“ipcs”。程序源代碼如下所示:

/*shmem.c*/

#include<sys/types.h>

#include<sys/ipc.h>

#include<sys/shm.h>

#include<stdio.h>

#include<stdlib.h>

#include<string.h>

#defineBUFFER_SIZE2048

intmain()

{

pid_tpid;

intshmid;

char*shm_addr;

charflag[]="WROTE";

char*buff;

/*創(chuàng)建共享內(nèi)存*/

if((shmid=shmget(IPC_PRIVATE,BUFFER_SIZE,0666))<0)

{

perror("shmget");

exit(1);

}

else

{

printf("Createshared-memory:%dn",shmid);

}

/*顯示共享內(nèi)存情況*/

system("ipcs-m");

pid=fork();

if(pid==-1)

{

perror("fork");

exit(1);

}

elseif(pid==0)/*子進程處理*/

{

/*映射共享內(nèi)存*/

if((shm_addr=shmat(shmid,0,0))==(void*)-1)

{

perror("Child:shmat");

exit(1);

}

else

{

printf("Child:Attachshared-memory:%pn",shm_addr);

}

system("ipcs-m");

/*通過檢查在共享內(nèi)存的頭部是否標(biāo)志字符串"WROTE"來確認(rèn)

父進程已經(jīng)向共享內(nèi)存寫入有效數(shù)據(jù)*/

while(strncmp(shm_addr,flag,strlen(flag)))

{

printf("Child:Waitforenabledata...n");

sleep(5);

}

/*獲取共享內(nèi)存的有效數(shù)據(jù)并顯示*/

strcpy(buff,shm_addr+strlen(flag));

printf("Child:Shared-memory:%sn",buff);

/*解除共享內(nèi)存映射*/

if((shmdt(shm_addr))<0)

{

perror("shmdt");

exit(1);

}

else

{

printf("Child:Deattachshared-memoryn");

}

system("ipcs-m");

/*刪除共享內(nèi)存*/

if(shmctl(shmid,IPC_RMID,NULL)==-1)

{

perror("Child:shmctl(IPC_RMID)n");

exit(1);

}

else

{

printf("Deleteshared-memoryn");

}

system("ipcs-m");

}

else/*父進程處理*/

{

/*映射共享內(nèi)存*/

if((shm_addr=shmat(shmid,0,0))==(void*)-1)

{

perror("Parent:shmat");

exit(1);

}

else

{

printf("Parent:Attachshared-memory:%pn",shm_addr);

}

sleep(1);

printf("nInputsomestring:n");

fgets(buff,BUFFER_SIZE,stdin);

strncpy(shm_addr+strlen(flag),buff,strlen(buff));

strncpy(shm_addr,flag,strlen(flag));

/*解除共享內(nèi)存映射*/

if((shmdt(shm_addr))<0)

{

perror("Parent:shmdt");

exit(1);

}

else

{

printf("Parent:Deattachshared-memoryn");

}

system("ipcs-m");

waitpid(pid,NULL,0);

printf("Finishedn");

}

exit(0);

}

下面是運行結(jié)果。從該結(jié)果可以看出,nattch的值隨著共享內(nèi)存狀態(tài)的變化而變化,共享內(nèi)存的值根據(jù)不同的系統(tǒng)會有所不同。

$./shmem

Createshared-memory:753665

/*在剛創(chuàng)建共享內(nèi)存時(尚未有任何地址映射)共享內(nèi)存的情況*/

------SharedMemorySegments--------

keyshmidownerpermsbytesnattchstatus

0x00000000753665david66620480

Child:Attachshared-memory:0xb7f59000/*共享內(nèi)存的映射地址*/

Parent:Attachshared-memory:0xb7f59000

/*在父子進程中進行共享內(nèi)存的地址映射之后共享內(nèi)存的情況*/

------SharedMemorySegments--------

keyshmidownerpermsbytesnattchstatus

0x00000000753665david66620482

Child:Waitforenabledata...

Inputsomestring:

Hello/*用戶輸入字符串“Hello”*/

Parent:Deattachshared-memory

/*在父進程中解除共享內(nèi)存的映射關(guān)系之后共享內(nèi)存的情況*/

------SharedMemorySegments--------

keyshmidownerpermsbytesnattchstatus

0x00000000753665david66620481

/*在子進程中讀取共享內(nèi)存的有效數(shù)據(jù)并打印*/

Child:Shared-memory:hello

Child:Deattachshared-memory

/*在子進程中解除共享內(nèi)存的映射關(guān)系之后共享內(nèi)存的情況*/

------SharedMemorySegments--------

keyshmidownerpermsbytesnattchstatus

0x00000000753665david66620480

Deleteshared-memory

/*在刪除共享內(nèi)存之后共享內(nèi)存的情況*/

------SharedMemorySegments--------

keyshmidownerpermsbytesnattchstatus

Finished

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

LED驅(qū)動電源的輸入包括高壓工頻交流(即市電)、低壓直流、高壓直流、低壓高頻交流(如電子變壓器的輸出)等。

關(guān)鍵字: 驅(qū)動電源

在工業(yè)自動化蓬勃發(fā)展的當(dāng)下,工業(yè)電機作為核心動力設(shè)備,其驅(qū)動電源的性能直接關(guān)系到整個系統(tǒng)的穩(wěn)定性和可靠性。其中,反電動勢抑制與過流保護是驅(qū)動電源設(shè)計中至關(guān)重要的兩個環(huán)節(jié),集成化方案的設(shè)計成為提升電機驅(qū)動性能的關(guān)鍵。

關(guān)鍵字: 工業(yè)電機 驅(qū)動電源

LED 驅(qū)動電源作為 LED 照明系統(tǒng)的 “心臟”,其穩(wěn)定性直接決定了整個照明設(shè)備的使用壽命。然而,在實際應(yīng)用中,LED 驅(qū)動電源易損壞的問題卻十分常見,不僅增加了維護成本,還影響了用戶體驗。要解決這一問題,需從設(shè)計、生...

關(guān)鍵字: 驅(qū)動電源 照明系統(tǒng) 散熱

根據(jù)LED驅(qū)動電源的公式,電感內(nèi)電流波動大小和電感值成反比,輸出紋波和輸出電容值成反比。所以加大電感值和輸出電容值可以減小紋波。

關(guān)鍵字: LED 設(shè)計 驅(qū)動電源

電動汽車(EV)作為新能源汽車的重要代表,正逐漸成為全球汽車產(chǎn)業(yè)的重要發(fā)展方向。電動汽車的核心技術(shù)之一是電機驅(qū)動控制系統(tǒng),而絕緣柵雙極型晶體管(IGBT)作為電機驅(qū)動系統(tǒng)中的關(guān)鍵元件,其性能直接影響到電動汽車的動力性能和...

關(guān)鍵字: 電動汽車 新能源 驅(qū)動電源

在現(xiàn)代城市建設(shè)中,街道及停車場照明作為基礎(chǔ)設(shè)施的重要組成部分,其質(zhì)量和效率直接關(guān)系到城市的公共安全、居民生活質(zhì)量和能源利用效率。隨著科技的進步,高亮度白光發(fā)光二極管(LED)因其獨特的優(yōu)勢逐漸取代傳統(tǒng)光源,成為大功率區(qū)域...

關(guān)鍵字: 發(fā)光二極管 驅(qū)動電源 LED

LED通用照明設(shè)計工程師會遇到許多挑戰(zhàn),如功率密度、功率因數(shù)校正(PFC)、空間受限和可靠性等。

關(guān)鍵字: LED 驅(qū)動電源 功率因數(shù)校正

在LED照明技術(shù)日益普及的今天,LED驅(qū)動電源的電磁干擾(EMI)問題成為了一個不可忽視的挑戰(zhàn)。電磁干擾不僅會影響LED燈具的正常工作,還可能對周圍電子設(shè)備造成不利影響,甚至引發(fā)系統(tǒng)故障。因此,采取有效的硬件措施來解決L...

關(guān)鍵字: LED照明技術(shù) 電磁干擾 驅(qū)動電源

開關(guān)電源具有效率高的特性,而且開關(guān)電源的變壓器體積比串聯(lián)穩(wěn)壓型電源的要小得多,電源電路比較整潔,整機重量也有所下降,所以,現(xiàn)在的LED驅(qū)動電源

關(guān)鍵字: LED 驅(qū)動電源 開關(guān)電源

LED驅(qū)動電源是把電源供應(yīng)轉(zhuǎn)換為特定的電壓電流以驅(qū)動LED發(fā)光的電壓轉(zhuǎn)換器,通常情況下:LED驅(qū)動電源的輸入包括高壓工頻交流(即市電)、低壓直流、高壓直流、低壓高頻交流(如電子變壓器的輸出)等。

關(guān)鍵字: LED 隧道燈 驅(qū)動電源
關(guān)閉