1.TCP/IP簡介
TCP/IP協(xié)議源于1969年,是針對Internet開發(fā)的一種體系結構和協(xié)議標準,目的在于解決異種計算機網(wǎng)絡的通信問題。使得網(wǎng)絡在互聯(lián)時能為用戶提供一種通用、一致的通信服務。是Internet采用的協(xié)議標準。
TCP/IP是一組通信協(xié)議的代名詞,是由一系列協(xié)議組成的協(xié)議簇。它本身指兩個協(xié)議集:
TCP(傳輸控制協(xié)議)。
? IP(互聯(lián)網(wǎng)絡協(xié)議)。
TCP/IP協(xié)議的基本傳輸單位是數(shù)據(jù)包(Datagram)。
TCP/IP傳輸協(xié)議,即傳輸控制/網(wǎng)絡協(xié)議,也叫作網(wǎng)絡通訊協(xié)議。它是在網(wǎng)絡的使用中的最基本的通信協(xié)議。TCP/IP傳輸協(xié)議對互聯(lián)網(wǎng)中各部分進行通信的標準和方法進行了規(guī)定。并且,TCP/IP傳輸協(xié)議是保證網(wǎng)絡數(shù)據(jù)信息及時、完整傳輸?shù)膬蓚€重要的協(xié)議。TCP/IP傳輸協(xié)議是嚴格來說是一個四層的體系結構,應用層、傳輸層、網(wǎng)絡層和數(shù)據(jù)鏈路層都包含其中。
2.獲取本地網(wǎng)卡信息
??獲取本地網(wǎng)卡信息的方法有很多種,在Linux命令行下我們可以通過ifconfig命令查詢網(wǎng)卡信息。
2.1 通過ioctl函數(shù)獲取網(wǎng)卡信息
??ioctl(input/output control)是一個專用于設備輸入輸出操作的系統(tǒng)調(diào)用,該調(diào)用傳入一個跟設備有關的請求碼,系統(tǒng)調(diào)用的功能完全取決于請求碼。
- ioctl函數(shù)原型:
#include
int ioctl(int fd, unsigned long request, ...);
形參:fd --文件描述符
request --請求命令
第三個參數(shù)為可變參數(shù),該參數(shù)填寫取決于request 命令;
返回值:一般成功返回0
網(wǎng)絡相關的請求劃分為6 類:
- 套接口操作
- 文件操作
- 接口操作
- ARP 高速緩存操作
- 路由表操作
- 流系統(tǒng)
下表列出了網(wǎng)絡相關ioctl 請求的request 參數(shù)以及arg 地址必須指向的數(shù)據(jù)類型:
獲取網(wǎng)卡信息示例:
#include
#include
#include
#include
#include
#include
#include
#include
int main()
{
int i=0;
int sockfd;
/*創(chuàng)建網(wǎng)絡套接字*/
if((sockfd = socket(AF_INET, SOCK_STREAM,0))0)
{
printf("socket errorn");
return -1;
}
struct ifreq ifcu_req[4];//網(wǎng)卡信息結構體
struct ifconf ifc=
{
.ifc_len=sizeof(ifcu_req),//緩沖區(qū)大小
.ifc_req=ifcu_req,
};
struct ifreq b_addr;
int ret=ioctl(sockfd,SIOCGIFCONF, &ifc);//獲取網(wǎng)絡接口信息
struct sockaddr boardaddr;
struct sockaddr_in addr;
printf("ret=%dn",ret);
char mac[6];
int j=0;
int count=ifc.ifc_len/sizeof(struct ifreq);//計算獲取到的網(wǎng)卡信息個數(shù)
for(i=0;i
3.域名解析
域名(英語:Domain Name),又稱網(wǎng)域,是由一串用點分隔的名字組成的Internet上某一臺計算機或計算機組的名稱,用于在數(shù)據(jù)傳輸時對計算機的定位標識(有時也指地理位置)。
由于IP地址具有不方便記憶并且不能顯示地址組織的名稱和性質(zhì)等缺點,人們設計出了域名,并通過網(wǎng)域名稱系統(tǒng)(DNS,Domain Name System)來將域名和IP地址相互映射,使人更方便地訪問互聯(lián)網(wǎng),而不用去記住能夠被機器直接讀取的IP地址數(shù)串。
#include
extern int h_errno;
struct hostent *gethostbyname(const char *name);
函數(shù)功能:域名解析
形參:name --域名
返回值:
struct hostent {
char *h_name; /* 主機的正式名稱 */
char **h_aliases; /* 別名列表*/
int h_addrtype; /* 主機地址類型*/
int h_length; /* 地址長度*/
char **h_addr_list; /*地址列表 */
}
void herror(const char *s); //錯誤輸出
const char *hstrerror(int err);//根據(jù)錯誤編號返回錯誤消息字符串
示例
#include
#include
#include
#include
#include
#include
int main(int argc,char *argv[])
{
if(argc!=2)
{
printf("格式:./app n");
return 0;
}
//域名解析
struct hostent *host_info=gethostbyname(argv[1]);
if(host_info==NULL)
{
printf("err=%d,%sn",h_errno,hstrerror(h_errno));
return 0;
}
int i=0;
struct in_addr addr;
printf("主機名:%sn",host_info->h_name);
for(i=0;host_info->h_aliases[i]!=0;i++)
{
printf("主機別名:%sn",host_info->h_aliases[i]);
}
for(i=0;host_info->h_addr_list[i]!=0;i++)
{
memcpy(&addr,host_info->h_addr_list[i],sizeof(addr));
printf("ip地址:%sn",inet_ntoa(addr));
}
}
運行效果:
獲取邦定ip地址信息getsockname
getsockname()函數(shù)用于獲取一個套接字的名字。它用于一個已捆綁或已連接套接字,本地地址將被返回。本調(diào)用特別適用于如下情況:未調(diào)用bind()就調(diào)用了connect(),這時唯有getsockname()調(diào)用可以獲知系統(tǒng)內(nèi)定的本地地址。在返回時,namelen參數(shù)包含了名字的實際字節(jié)數(shù)。
#include
int getsockname(int sockfd, struct sockaddr *addr, socklen_t *addrlen);
函數(shù)功能:獲取sockfd綁定的ip地址和端口號信息
形 參:sockfd --網(wǎng)絡套接字
addr --保存返回的ip地址和端口號信息
addrlen --addr緩沖區(qū)大小(必須由用戶設置大小,函數(shù)調(diào)用成功返回實際addr大小)
返回值:成功返回0,失敗-1
示例:
#include
#include /* See NOTES */
#include
#include
#include
#include
#include /* superset of previous */
#include
int main(int argc,char *argv[])
{
if(argc!=3)
{
printf("格式:./app n");
return 0;
}
/*創(chuàng)建網(wǎng)絡套接字*/
int sockfd=socket(AF_INET, SOCK_STREAM,0);
if(sockfd==-1)
{
printf("創(chuàng)建網(wǎng)絡套接字失敗n");
return 0;
}
/*連接服務器*/
struct sockaddr_in addr=
{
.sin_family=AF_INET,//IPV4
.sin_port=htons(atoi(argv[1])),//服務器端口號
.sin_addr=
{
.s_addr=inet_addr(argv[2]),//服務器IP
}
};
if(connect(sockfd,(struct sockaddr *)&addr,sizeof(addr)))
{
printf("連接服務器失敗n");
return 0;
}
printf("服務器連接成功n");
struct sockaddr_in c_addr;
socklen_t addrlen=sizeof(c_addr);
getsockname(sockfd,(struct sockaddr *)&c_addr, &addrlen);
printf("本地信息%s:%dn",inet_ntoa(c_addr.sin_addr),ntohs(c_addr.sin_port));
while(1)
{
}
}
-
嵌入式
+關注
關注
5082文章
19104瀏覽量
304777 -
網(wǎng)卡
+關注
關注
4文章
307瀏覽量
27374 -
編程
+關注
關注
88文章
3614瀏覽量
93685 -
TCP
+關注
關注
8文章
1353瀏覽量
79054
發(fā)布評論請先 登錄
相關推薦
評論