**
套介面建立後,就如同乙個檔案描述符,我們可以使用同樣的io函式進行讀寫,關閉操作。其實,和引用乙個已經開啟的檔案一樣,套介面也是通過檔案描述符來引用的,而且兩者的檔案描述符共享乙個「數字空間」,比如說不能既開啟乙個檔案描述符為4的套介面,又開啟乙個檔案描述符為4的檔案。
套介面和已經開啟的檔案的區別:
1.不能在套介面上呼叫函式lseek()當然對於管道也不能呼叫這個函式。
2.套介面可以和網路位址關聯,但是檔案和管道卻不可以。
3.套介面有很多可以通過ioctl()進行查詢和設定的選項。
4.套介面必須在正確的狀態寫才能進行輸入輸出,但是已經開啟的檔案可以在任何的時候進行讀寫操作。
呼叫open()函式開啟乙個新檔案,linux核心會返回乙個當前系統可用的最小的檔案描述符。比如如果關閉了標準輸入(檔案描述符0),又立即開啟乙個新檔案,那麼新檔案的檔案描述符就是0.
另外要注意的是linux核心在分配檔案描述符的時候,並不區分這個描述符是分配給套介面還是給已經開啟的檔案的。
我們知道,使用int pipe(int fileds[2]);函式可以建立管道,如果這個函式呼叫成功,核心會返回兩個檔案描述符,fileds[0]表示管道讀出端的檔案描述符,fileds[1]表示管道寫入端的檔案描述符。所以可以看出管道是單向的,任何的反方向操作會導致錯誤。
但是套介面不同,他可以進行雙向通訊。這個也是他和管道的根本差異。
建立乙個套介面使用以下的函式:
#include #include int socketpair(int domain,int type,int protocol,int sv[2]);
下面我們來展示乙個socketpair的例子:
#include #include #include #include #include #include #include int main(int argc, char const *argv)printf("s[0]=%d\n", s[0]);
printf("s[1]=%d\n", s[1]);
return 0;
}
其中af_local套介面又被稱為是unix套介面,所以使用af_unix和使用af_local都是一樣的。不過建議使用af_local。
下面我們來展示一下使用套介面實現i/o
………………undone(此處**待新增)
我們來看看如何關閉套介面
當我們從管道讀取輸入的時候,讀取程序受到檔案結束標識以後就知道沒有後續檔案了,因為檔案描述符是由寫程序關閉管道的寫段的時候傳送的。套介面的關閉類似,當在套介面傳送端關閉後,接受端就會受到檔案結束標識,但是這種關閉方式不適用所有的情況。close終止了資料傳送的兩個方向:讀和寫,由於tcp是全雙工的,在很多的情況下,本地程序要通知遠端端點已經完成了資料的傳送工作,但是仍然等待從遠端端點接受資料,在這種情況下,我們需要對套介面進行半關閉操作,就需要用到shutdown函式:
#include int shutdown(int s, int how);
其中s是需要進行半關閉的套介面,需要進行關閉的方式是how,引數how的取值請看下表:值巨集
描述0shut_rd
程序不能對指定套介面進行讀操作
1shut_wr
進行不能對指定套介面進行寫操作
2shut_rdwr
程序不能對指定套介面進行讀寫操作
大家可以看出,當how引數的取值為2的時候,shutdown函式和close函式一樣了。下面舉乙個例子:
int state;int s;
state=shutdown(s,shut_wr);
if(z == -1)
下面我們來看看如何處理複製套介面的情況:
如果呼叫函式dup或者dup2的話,那麼只有最後乙個close呼叫才可以關閉套介面,系統這樣做,是因為他認為其他複製的檔案描述符仍然在使用中,如下所示:
int s; //已經存在的套介面
int d; //被複製的套介面
d=dup(s); //複製套介面
close(s) // 套介面並未被關閉
close(d) //套介面被關閉
在上面的例子中,第乙個close函式呼叫並沒有關閉套介面,其實無論先關閉s還是先關閉d,沒任何區別。而只有當最後乙個檔案描述符被關閉的時候,套介面才是被真正的關閉了。但是如果使用shutdown函式的話,就沒有這個問題。:
int s
int d;
d=dup(s);
shutdown(s,shut_rdwr);
即使套介面s仍然通過檔案描述符d開啟,shutdown函式仍然立即將套介面徹底關閉。
建議:總是使用shutdown函式來代替close函式。
當呼叫shutdown函式的時候,如果給定的套介面不是有效的檔案描述符,返回ebadf錯誤。
如果給定的檔案描述符不是套介面,返回enotsock錯誤
如果套介面出於非連線狀態,返回enotconn錯誤。
注意:即便是使用引數為shut_rdwr的時候,函式shutdown也不會釋放檔案描述符,在使用close釋放檔案描述符之前,他一直可用。
Linux Socket學習 域和套介面簡介
套介面建立後,就如同乙個檔案描述符,我們可以使用同樣的io函式進行讀寫,關閉操作。其實,和引用乙個已經開啟的檔案一樣,套介面也是通過檔案描述符來引用的,而且兩者的檔案描述符共享乙個 數字空間 比如說不能既開啟乙個檔案描述符為4的套介面,又開啟乙個檔案描述符為4的檔案。套介面和已經開啟的檔案的區別 1...
Linux socket 傳輸和接受結構體
linux程式設計 linux socket send and recevie structure 最近在開發乙個linux下的聊天軟體,好久沒有做c語言的開發了,感覺到很多東西已經生疏了,這下又碰到用socket傳遞結構體的問題,google了一下,發現也有不少朋友遇到同樣的問題,所以就打算寫出自...
Linux Socket學習 為套介面繫結位址
當我們使用socket函式建立乙個套介面之後,這個套介面就處於無名狀態,雖然之前我們提到即使沒有位址,套介面也能使用,但是這個只限於套介面對在同乙個linux核心中,如果位於兩台不同的主機的套介面需要連線,而又沒有位址,那麼就無法工作。函式bind的作用就是為無名套介面分配位址,語法如下 inclu...