<ruby id="bdb3f"></ruby>

    <p id="bdb3f"><cite id="bdb3f"></cite></p>

      <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
        <p id="bdb3f"><cite id="bdb3f"></cite></p>

          <pre id="bdb3f"></pre>
          <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

          <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
          <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

          <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                <ruby id="bdb3f"></ruby>

                企業??AI智能體構建引擎,智能編排和調試,一鍵部署,支持知識庫和私有化部署方案 廣告
                ## 實驗步驟 (1)在ubuntu下,用系統提供的sem_open()、sem_close()、sem_wait()和sem_post()等信號量相關的系統調用編寫pc.c程序。 (2)在ubuntu上編譯并運行pc.c,檢查運行結果。 ### 終端也是臨界資源 用printf()向終端輸出信息是很自然的事情,但當多個進程同時輸出時,終端也成為了一個臨界資源,需要做好互斥保護,否則輸出的信息可能錯亂。 另外,printf()之后,信息只是保存在輸出緩沖區內,還沒有真正送到終端上,這也可能造成輸出信息時序不一致。用fflush(stdout)可以確保數據送到終端。 本次實驗相較于往屆已極大地簡化,畢竟時間有限,所以不用在Linux0.11下實現信號量(里面沒有sem_open()等系統調用,需要自己添加),僅需要在Ubantu下運行生產者,消費者的相關程序。 首先介紹一下所需函數 ~~~ int fseek(FILE *stream, long offset, int fromwhere); 函數設置文件指針stream的位置。 如果執行成功,stream將指向以fromwhere為基準,偏移offset(指針偏移量)個字節的位置,函數返回0。 如果執行失敗(比如offset超過文件自身大小),則不改變stream指向的位置,函數返回一個非0值。 size_t fread(void *buffer,size_t size,size_t count, FILE *stream ); ? buffer ? 是讀取的數據存放的內存的指針 ? size ? ? 是每次讀取的字節數 ? count ? ?是讀取次數 ? stream ? 是要讀取的文件的指針 從一個文件流中讀數據,最多讀取count個元素,每個元素size字節,如果調用成功返回實際讀取到的元素個數,如果不成功或讀到文件末尾返回 0。 size_t fwrite(const void* buffer, size_t size, size_t count, FILE* stream); (1)buffer:是一個指針,對fwrite來說,是要獲取數據的地址; (2)size:要寫入內容的單字節數; (3)count:要進行寫入size字節的數據項的個數; (4)stream:目標文件指針; (5)返回實際寫入的數據項個數count。 ~~~ 算法的思想是:建立一個文件緩沖區,0~9位存儲生產出的數據,第10位存儲當前讀到的位置;因為緩沖區是覆蓋寫入,例如當消費者消費到第6位,而生產者此時可以生產覆蓋前5位,但消費者消費是順序消費的,必須要讀到緩沖區尾才可以再從頭讀。 這就有必要存儲當前讀取的位置(因為進程可能被中斷,下次再來就不知道讀到哪里了),所以下面要執行兩次,第一次讀出當前所讀位置,再根據此位置計算位偏移。 ~~~ fseek( fp, 10*sizeof(int), SEEK_SET ); fread( &Outpos, sizeof(int), 1, fp); fseek( fp, Outpos*sizeof(int), SEEK_SET ); fread( &costnum, sizeof(int), 1, fp); ~~~ pc.c ~~~ #define __LIBRARY__ #include <sys/stat.h> #include <sys/types.h> #include <unistd.h> #include <fcntl.h> #include <stdio.h> #include <stdlib.h> #include <semaphore.h> #define Total 500 #define PNUM 5 #define BUFFERSIZE 10 /* */ int main() { int i, j, k; int costnum; int Outpos = 0; int Inpos = 0; sem_t *empty, *full, *mutex; FILE *fp = NULL; empty =(sem_t *)sem_open("empty", O_CREAT, 0064, 10); full = (sem_t *)sem_open("full", O_CREAT, 0064, 0); mutex = (sem_t *)sem_open("mutex",O_CREAT, 0064, 1); fp=fopen("FileBuffer.txt", "wb+"); fseek( fp, 10*sizeof(int) , SEEK_SET ); fwrite( &Outpos, sizeof(int), 1, fp); fflush(fp); if( !fork() ) { for( i = 0 ; i < Total; i++) { sem_wait(empty); sem_wait(mutex); fseek( fp, Inpos * sizeof(int), SEEK_SET ); fwrite( &i, sizeof(int), 1, fp ); fflush(fp); Inpos = ( Inpos + 1 ) % BUFFERSIZE; sem_post(mutex); sem_post(full); } exit(0); } for( k = 0; k < PNUM ; k++ ) { if( !fork() ) { for( j = 0; j < Total/PNUM; j++ ) { sem_wait(full); sem_wait(mutex); /* fseek( fp , 10*sizeof(int) , SEEK_SET ); if(!fread( &outlocate, sizeof(int),1, fp)) { printf("read error!\n"); exit(1); } */ /* fseek(fp, outlocate*sizeof(int), SEEK_SET ); if(!fread( &costnum, sizeof(int),1, fp)) { printf("read error!\n"); exit(1); } */ fflush(stdout); fseek( fp, 10*sizeof(int), SEEK_SET ); fread( &Outpos, sizeof(int), 1, fp); fseek( fp, Outpos*sizeof(int), SEEK_SET ); fread( &costnum, sizeof(int), 1, fp); printf("%d: %d\n",getpid(),costnum); fflush(stdout); Outpos = (Outpos + 1) % BUFFERSIZE; fseek( fp, 10*sizeof(int), SEEK_SET ); fwrite( &Outpos, sizeof(int),1, fp ); fflush(fp); sem_post(mutex); sem_post(empty); } exit(0); } } wait(NULL); wait(NULL); wait(NULL); wait(NULL); wait(NULL); sem_unlink("empty"); sem_unlink("full"); sem_unlink("mutex"); fclose(fp); return 0; } ~~~ 附report 1.在pc.c中去掉所有與信號量有關的代碼,再運行程序,執行效果有變化嗎?為什么會這樣? 答:在去掉與信號量有關的代碼后,執行結果Customer的消費數據沒有按遞增的順序輸出,且fread()函數將產生錯誤。 因為沒有信號量P(S)控制,導致生產者可能在緩沖區滿后繼續生產,導致沒有被消費的數據被覆蓋,使得消費者消費的數據不是遞增序列。 同時,沒有信號量V(S)控制,導致消費者可能在讀取所有數據后仍然繼續讀取,導致讀取的數據無效。 沒有mutex信號量控制導致出現多進程并發訪問緩沖區,導致出現fread()錯誤。 2.這樣可行嗎?如果可行,那么它和標準解法在執行效果上會有什么不同?如果不可行,那么它有什么問題使它不可行? 答:這樣不可行。程序在某種情況下會出現死鎖狀態。 例如:當mutex = 1,并且生產者要進入生產一個數據,假設此時empty = 0,mutex = 0,P(empty)后小于0,生產者進程進入等待在信號量empty的等待隊列上面調用schedule(),可是此時并未解鎖,即mutex.value值仍然為0。它們都等待在信號量mutex上面。同理,消費者進程也是如此,若mutex.value = 1,full.value = 0,在執行完P(mutex)P(full)之后,mutex = 0,并且將消費者進程放入等待在信號量full的等待隊列上面,而此時也并未釋放mutex,因此消費者和生產者進程都等待在mutex信號量上面。進而產生饑餓狀態進入死鎖。
                  <ruby id="bdb3f"></ruby>

                  <p id="bdb3f"><cite id="bdb3f"></cite></p>

                    <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
                      <p id="bdb3f"><cite id="bdb3f"></cite></p>

                        <pre id="bdb3f"></pre>
                        <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

                        <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
                        <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

                        <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                              <ruby id="bdb3f"></ruby>

                              哎呀哎呀视频在线观看