信息安全設計基礎第十週學習總結

信息安全設計基礎第十週學習總結

【學習時間:8小時】  【學習內容:教材第十章 之 I/O總結;實驗樓私有課程《深刻理解計算機系統》 之 系統級I/O】html

1、教材內容

1.I/O重定向

【重定向實際上是unix系統優越性的一種體現(與管道類似);將一種操做的結果重定向到另一種操做上,這樣的思想保證了「專務專用」,將單個操做作到極致,又爲用戶本身提供了完善功能的平臺(好比重定向,好比管道)。】 - unix外殼提供了I/O重定向操做符,容許用戶將磁盤文件和標準輸入輸出鏈接起來。例如:node

ls > foo.txt;

使得外殼加載和執行ls程序,將標準輸出重定向到foo.txt。linux

  • 工做方式:web

    #include <unistd.h>
    int dup2(int oldfd,int newfd);

    拷貝描述符表項oldfd到描述符表項newfd,同時覆蓋掉newfd以前的內容。若是newfd已經打開,就先關閉newfd再進行操做。編程

  • 調用dup2(4,1)示例:

前提:假設描述符1(標準輸出)對應於文件A,4對應於文件B,A和B的引用計數等於1.ubuntu

過程:兩個描述符都指向文件B,文件A已經被關閉,它以前對應的文件表和v-node也已經被刪 除;文件B的引用計數增長,以後的任何標準輸出(描述符1)的數據都被重定向到文件B。安全

2.標準I/O庫

【以前的輸入輸出函數並無特定性,而是適用於一般狀況下的I/O;標準I/O庫針對I/O的具體狀況,分類給出了特定的I/O函數;從必定角度而言,是「高級」的I/O函數。另外,與此相關的「流」的概念是和指針很類似的,也是一種「抽象」。】併發

  • 總述:這個庫提供了unixI/O較高級別的替代。
  • 類型:
    • 打開和關閉文件的函數(fopen和fclose);
    • 讀和寫字節的函數(fread和fwrite);
    • 讀和寫字符串的函數(fgets和fputs)
  • 流的應用: 一個流就是指向一個FILE類型的結構的指針(好比,每有一個ASNI C文件打開,都會同時打開STDIN,STDOUT,STDERR三個流)。
    • 含義:流是對文件描述符和流緩衝區的抽象。(流緩衝區的目的和RIO相似,就是減小開銷較高的unix系統調用的數量)

3.關於輸入與輸出函數的一些矛盾點

【C語言編程的時候,常常會由於輸入域輸出交叉調用致使輸入或者輸出函數不能取到想要的值】app

  • 輸入函數不能緊跟在輸出函數以後——若是輸出函數以後沒有加上fflush,fseek,fsetpos等。前者是清空與流相關的緩衝區;後二者用lseek函數重置當前的文件位置;
  • 輸出函數不能緊跟在輸入函數以後——若是輸入函數以後沒有fseek,fsetpos,rewind等。

4.基於錯誤處理包裝函數

  • 思想:給定的基本級系統函數foo,咱們有相同參數的、函數名大寫的包裝函數Foo;包裝函數調用基本函數並檢查錯誤。若是發現了錯誤,包裝函數就終止進程並返回一條信息;當基本函數無誤的時候,包裝函數就返回調用者。(包裝函數被封裝在源文件csapp.c中)

5.unix系統中的錯誤處理

  • unix風格:例如fork函數和外套函數,返回值既包括錯誤代碼,又包括有用的結果。函數

    if((pid = wait(NULL))<0)
    {
        fprintf(stderr,"wait error:%s\n",strerror(errno));//將errno設置爲指向錯誤緣由的代碼
        exit(0);
    }
  • Posix風格:例如pthread,函數只返回調用成功(0)或者失敗(非0),任何有用的信息都返回在經過調用引用進來的參數中。
  • DNS風格:gethostbyname和gethostbyaddr檢索NDS(域名系統)庫;它們在錯誤的時候會返回NULL,並設置全局變量h_errno。
  • 錯誤處理包裝函數

    • unix風格

      pid_t Wait(int *status)
      {
          pid_t pid;
          if(pid = wait(status)<0)
              unix_error("wait error");
          return pid;
      }
    • Posix風格

      void Pthread_detach(pthread_t tid)
      {
          int rc;
          if(rc=pthread_detach(tid) != 0)
              posix_error(rc,"Pthread_detach error");
      }
    • DNS風格

      struct hostent *Gethostbyname(const char *name)
      {
          struct hostname *p;
          if((p = gethostbyname(name)) == NULL)
              dns_error("Gethostbyname error");
          return p;
      }

2、練習題

1.如何使用dup2將標準輸入重定向到描述符5?

【參考上面的函數,標準輸入的描述符爲0,則使用:

int dup2(5,0);

進行重定向。】

2.假設磁盤文件foo.txt由6個ASCII碼字符「foobar」組成,那麼下列程序的輸出是什麼?

#include "csapp.h"
int main()
{
    int fd1,fd2;
    char c;
    fd1 = Open("foobar.txt",O_RDONLY,0);
    fd2 = Open("foobar.txt",0_RDONLY,0);
    Read(fd2,&c,1);
    Dup(fd2,fd1);
    Read(fd1,&c,1);
    printf("c= %c\n",c);
    exit(0);
}

【fd1被重定向到了fd2,因此輸出的是第二個字母(以前的第一個字母‘f’已經被讀過了):‘o’】

3、課堂講解重點

1.man -k應用:

2.關於父子進程併發執行的問題:

【當父進程打開子進程以後,父子進程併發執行,並且,兩者結束的前後順序是不可控制的;最後,當子進程被打開以後,父子進程以後的部分是同樣的;並且,最後的結果前後沒法區分】

4、問題解決

  • 1.開始運行練習題10.1的代碼時,編譯出錯,顯示是由於沒法找到「csapp.h」文件

    #include "csapp.h"
    int main()
    {
        int fd1,fd2;
        fd1=Open("foo.txt",O_RDONLY,0);
        Close(fd1);
        fd2=Open("baz.txt",O_RDONLY,0);
        printf("fd2=%d\n",fd2);
        exit(0);
    }

    經過網上搜索,發現一篇博客給出瞭解答:

這一週老師給佈置了一個有關IO的Open函數的實驗,叫咱們本身到linux上去運行一下,結果在csapp.h這個頭文件上糾結了很久,在這裏特別總結一下,留個記念. 是csapp.h其實就是一堆頭文件的打包,在http://csapp.cs.cmu.edu/public/code.html 這裏能夠下載。這是《深刻理解計算機系統》配套網站,但有個疑問是csapp.h這個 是做者寫的?仍是出自unix的源代碼了?但毫無疑問他給咱們寫一些程序的編寫帶來了方便,有了它咱們就不必在寫那麼多頭文件了,一個就搞定。至於出處的話,就不糾結了,會用就行。

在linux下要怎麼使用頭文件了,linux應該沒有自帶csapp.h,因此要本身導入,我用的是fedora的,要放到 /usr/include的文件夾裏面。打開後這裏面有好多頭文件... (ubuntu下是/usr/lib,其餘版本的linux應該也是在usr的目錄下吧)。另外還有一點,要在頭文件的#end if前面加上一句#include <csapp.c>,由於那個頭文件要把csapp.c文件包含進去 這樣的話就能夠用了。

還有就是由於csapp.c中有關於線程的頭文件,在用gcc的時候最後要加上-lpthread 如 # gcc -o Ex Ex.c -lpthread

  • 2.在開始進行關於頭文件爲csapp.h的編程時,我遇到了以下的問題:

【也就是沒法經過「複製」——「粘貼」完成csapp.h的添加】 

【通過小組提問,發現能夠經過命令行終端的mv命令進行操做】

  • 3.在我進行第三次嘗試的時候,新的問題又出現了:linux系統沒法識別U盤,也沒法和主機共享文件夾。致使csapp.h文件沒法拷貝到虛擬機。  經過「百度經驗」,我按照指導下載並安裝了virtualbox 4.3.26 r98988版本的擴展包,以此安裝加強功能;然而安裝失敗。

  • 4.經過請教老師,發現是因爲本機電腦爲win8.1,裝載虛擬機限制比較多。此後,我又借用其餘同窗的電腦,在蘋果IOS系統下進行嘗試。

【結果失敗】

  • 5.仔細研究以後,我發現刪除掉csapp.h和csapp.c以後從新嘗試,則能夠運行出結果。(另:虛擬機與主機的文件交互目前還在嘗試)

心得

本次學習是對以前學習的精細化過程;由於知識性的新內容很少,因此我就把大部分精力放在了實踐上。對於課本上的代碼,儘可能去打出來運行;對於以前想嘗試但一直沒有嘗試的linux命令或者功能學習,盡力去練習。看似抓住的很少,然而不斷的嘗試和失敗再到成功,也是頗有教育意義的。

相關文章
相關標籤/搜索