侵權投訴

從Linux源碼分析bind系統調用

39度創意研究所 2020-10-16 11:08 次閲讀

前言

筆者一直覺得如果能知道從應用到框架再到操作系統的每一處代碼,是一件Exciting的事情。 今天筆者就來從Linux源碼的角度看下Server端的Socket在進行bind的時候到底做了哪些事情(基於Linux 3.10內核)。

一個最簡單的Server端例子

眾所周知,一個Server端Socket的建立,需要socket、bind、listen、accept四個步驟。 


代碼如下:

  void start_server(){      // server fd      int sockfd_server;      // accept fd       int sockfd;      int call_err;      struct sockaddr_in sock_addr;        sockfd_server = socket(AF_INET,SOCK_STREAM,0);      memset(&sock_addr,0,sizeof(sock_addr));      sock_addr.sin_family = AF_INET;      sock_addr.sin_addr.s_addr = htonl(INADDR_ANY);      sock_addr.sin_port = htons(SERVER_PORT);      // 這邊就是我們今天的聚焦點bind      call_err=bind(sockfd_server,(struct sockaddr*)(&sock_addr),sizeof(sock_addr));      if(call_err == -1){          fprintf(stdout,"bind error!\n");          exit(1);      }      // listen      call_err=listen(sockfd_server,MAX_BACK_LOG);      if(call_err == -1){          fprintf(stdout,"listen error!\n");          exit(1);      }  }

首先我們通過socket系統調用創建了一個socket,其中指定了SOCK_STREAM,而且最後一個參數為0,也就是建立了一個通常所有的TCP Socket。在這裏,我們直接給出TCP Socket所對應的ops也就是操作函數。 


如果你想知道上圖中的結構是怎麼來的,可以看下筆者以前的博客:

  //my.oschina.net/alchemystar/blog/1791017  

 

bind系統調用

bind將一個本地協議地址(protocol:ip:port)賦予一個套接字。例如32位的ipv4地址或128位的ipv6地址+16位的TCP活UDP端口號。

  #include   // 返回,若成功則為0,若出錯則為-1  int bind(int sockfd, const struct sockaddr *myaddr, socklen_t addrlen); 

好了,我們直接進入Linux源碼調用棧吧。

  bind  	// 這邊由系統調用的返回值會被glibc的INLINE_SYSCALL包一層  	// 若有錯誤,則設置返回值為-1,同時將系統調用的返回值的絕對值設置給errno  	|->INLINE_SYSCALL (bind......);  		|->SYSCALL_DEFINE3(bind......);  			/* 檢測對應的描述符fd是否存在,不存在,返回-BADF  			|->sockfd_lookup_light  			|->sock->ops->bind(inet_stream_ops)  				|->inet_bind  					|->AF_INET兼容性檢查  					|-><1024端口權限檢查  					/* bind端口號校驗or選擇(在bind為0的時候)  					|->sk->sk_prot->get_port(inet_csk_get_port)

inet_bind

inet_bind這個函數主要做了兩個操作,一是檢測是否允許bind,而是獲取可用的端口號。這邊值得注意的是。如果我們設置需要bind的端口號為0,那麼Kernel會幫我們隨機選擇一個可用的端口號來進行bind!

  // 讓系統隨機選擇可用端口號  sock_addr.sin_port = 0;  call_err=bind(sockfd_server,(struct sockaddr*)(&sock_addr),sizeof(sock_addr));  

讓我們看下inet_bind的流程 


值得注意的是,由於對於<1024的端口號需要CAP_NET_BIND_SERVICE,我們在監聽80端口號(例如啓動nginx時候),需要使用root用户或者賦予這個可執行文件CAP_NET_BIND_SERVICE權限。

  use root    or  setcap cap_net_bind_service=+eip ./nginx 

我們的bind允許綁定到0.0.0.0即INADDR_ANY這個地址上(一般都用這個),它意味着內核去選擇IP地址。對我們最直接的影響如下圖所示: 


然後,我們看下一個比較複雜的函數,即可用端口號的選擇過程inet_csk_get_port (sk->sk_prot->get_port)

inet_csk_get_port

第一段,如果bind port為0,隨機搜索可用端口號

直接上源碼,第一段代碼為端口號為0的搜索過程

  // 這邊如果snum指定為0,則隨機選擇端口  int inet_csk_get_port(struct sock *sk, unsigned short snum)  {  	......  	// 這邊net_random()採用prandom_u32,是偽(pseudo)隨機數  	smallest_rover = rover = net_random() % remaining + low;  	smallest_size = -1;  	// snum=0,隨機選擇端口的分支  	if(!sum){  		// 獲取內核設置的端口號範圍,對應內核參數/proc/sys/net/ipv4/ip_local_port_range   		inet_get_local_port_range(&low,&high);  		......  		do{  			if(inet_is_reserved_local_port(rover)  				goto next_nonlock; // 不選擇保留端口號  			......  			inet_bind_bucket_for_each(tb, &head->chain)  				// 在同一個網絡命名空間下存在和當前希望選擇的port rover一樣的port  				if (net_eq(ib_net(tb), net) && tb->port == rover) {  					// 已經存在的sock和當前新sock都開啓了SO_REUSEADDR,且當前sock狀態不為listen  					// 或者  					// 已經存在的sock和當前新sock都開啓了SO_REUSEPORT,而且兩者都是同一個用户  					if (((tb->fastreuse > 0 &&  					      sk->sk_reuse &&  					      sk->sk_state != TCP_LISTEN) ||  					     (tb->fastreuseport > 0 &&  					      sk->sk_reuseport &&  					      uid_eq(tb->fastuid, uid))) &&  					    (tb->num_owners < smallest_size || smallest_size == -1)) {  					   // 這邊是選擇一個最小的num_owners的port,即同時bind或者listen最小個數的port  					   // 因為一個端口號(port)在開啓了so_reuseaddr/so_reuseport之後,是可以多個進程同時使用的  						smallest_size = tb->num_owners;  						smallest_rover = rover;  						if (atomic_read(&hashinfo->bsockets) > (high - low) + 1 &&  						    !inet_csk(sk)->icsk_af_ops->bind_conflict(sk, tb, false)) {  						    // 進入這個分支,表明可用端口號已經不夠了,同時綁定當前端口號和之前已經使用此port的不衝突,則我們選擇這個端口號(最小的)  							snum = smallest_rover;  							goto tb_found;  						}  					}  					// 若端口號不衝突,則選擇這個端口  					if (!inet_csk(sk)->icsk_af_ops->bind_conflict(sk, tb, false)) {  						snum = rover;  						goto tb_found;  					}  					goto next;  				}  			break;  			// 直至遍歷完所有的可用port  		} while (--remaining > 0);  	}  	.......  }

由於,我們在使用bind的時候很少隨機端口號(在TCP服務器來説尤其如此),這段代碼筆者就註釋一下。一般只有一些特殊的遠程過程調用(RPC)中會使用隨機Server端隨機端口號。

第二段,找到端口號或已經指定

  have_snum:  	inet_bind_bucket_for_each(tb, &head->chain)  			if (net_eq(ib_net(tb), net) && tb->port == snum)  				goto tb_found;  	}  	tb = NULL;  	goto tb_not_found  tb_found:  	// 如果此port已被bind  	if (!hlist_empty(&tb->owners)) {  		// 如果設置為強制重用,則直接成功  		if (sk->sk_reuse == SK_FORCE_REUSE)  			goto success;  	}  	if (((tb->fastreuse > 0 &&  		      sk->sk_reuse && sk->sk_state != TCP_LISTEN) ||  		     (tb->fastreuseport > 0 &&  		      sk->sk_reuseport && uid_eq(tb->fastuid, uid))) &&  		    smallest_size == -1) {  		    // 這個分支表明之前bind的port和當前sock都設置了reuse同時當前sock狀態不為listen  			// 或者同時設置了reuseport而且是同一個uid(注意,設置了reuseport後,可以同時listen同一個port了)  			goto success;  	} else {  			ret = 1;  			// 檢查端口是否衝突  			if (inet_csk(sk)->icsk_af_ops->bind_conflict(sk, tb, true)) {  				if (((sk->sk_reuse && sk->sk_state != TCP_LISTEN) ||  				     (tb->fastreuseport > 0 &&  				      sk->sk_reuseport && uid_eq(tb->fastuid, uid))) &&  				    smallest_size != -1 && --attempts >= 0) {  				    // 若衝突,但是設置了reuse非listen狀態或者設置了reuseport且出在同一個用户下  				    // 則可以進行重試  					spin_unlock(&head->lock);  					goto again;  				}    				goto fail_unlock;  			}  			// 不衝突,走下面的邏輯  		}  tb_not_found:  	if (!tb && (tb = inet_bind_bucket_create(hashinfo->bind_bucket_cachep,  					net, head, snum)) == NULL)  			goto fail_unlock;  	// 設置fastreuse  	// 設置fastreuseport  success:  	......  	// 將當前sock鏈入tb->owner,同時tb->num_owners++  	inet_bind_hash(sk, tb, snum);  	ret = 0;  	// 返回bind(綁定)成功  	return ret;

判斷端口號是否衝突

在上述源碼中,判斷端口號時否衝突的代碼為

  inet_csk(sk)->icsk_af_ops->bind_conflict 也即 inet_csk_bind_conflict  int inet_csk_bind_conflict(const struct sock *sk,  			   const struct inet_bind_bucket *tb, bool relax){  	......  	sk_for_each_bound(sk2, &tb->owners) {  			// 這邊判斷表明,必須同一個接口(dev_if)才進入下內部分支,也就是説不在同一個接口端口的不衝突  			if (sk != sk2 &&  		    !inet_v6_ipv6only(sk2) &&  		    (!sk->sk_bound_dev_if ||  		     !sk2->sk_bound_dev_if ||  		     sk->sk_bound_dev_if == sk2->sk_bound_dev_if))   		     {  		     	if ((!reuse || !sk2->sk_reuse ||  			    sk2->sk_state == TCP_LISTEN) &&  			    (!reuseport || !sk2->sk_reuseport ||  			    (sk2->sk_state != TCP_TIME_WAIT &&  			     !uid_eq(uid, sock_i_uid(sk2))))) {  			   // 在有一方沒設置reuse且sock2狀態為listen 同時  			   // 有一方沒設置reuseport且sock2狀態不為time_wait同時兩者的uid不一樣的時候  				const __be32 sk2_rcv_saddr = sk_rcv_saddr(sk2);  				if (!sk2_rcv_saddr || !sk_rcv_saddr(sk) ||  				 	 // ip地址一樣,才算衝突  				    sk2_rcv_saddr == sk_rcv_saddr(sk))  					break;  			}  			// 非放鬆模式,ip地址一樣,才算衝突  			......  		  	return sk2 != NULL;  	}  	......  }

上面代碼的邏輯如下圖所示: 

SO_REUSEADDR和SO_REUSEPORT

上面的代碼有點繞,筆者就講一下,對於我們日常開發要關心什麼。 我們在上面的bind裏面經常見到sk_reuse和sk_reuseport這兩個socket的Flag。這兩個Flag能夠決定是否能夠bind(綁定)成功。這兩個Flag的設置在C語言裏面如下代碼所示:

   setsockopt(sockfd_server, SOL_SOCKET, SO_REUSEADDR, &(int){ 1 }, sizeof(int));   setsockopt(sockfd_server, SOL_SOCKET, SO_REUSEPORT, &(int){ 1 }, sizeof(int));  

在原生JAVA

   // java8中,原生的socket並不支持so_reuseport   ServerSocket server = new ServerSocket(port);   server.setReuseAddress(true);  

在Netty(Netty版本 >= 4.0.16且Linux內核版本>=3.9以上)中,可以使用SO_REUSEPORT。

SO_REUSEADDR

在之前的源碼裏面,我們看到判斷bind是否衝突的時候,有這麼一個分支

  (!reuse || !sk2->sk_reuse ||  			    sk2->sk_state == TCP_LISTEN) /* 暫忽略reuseport */){  	// 即有一方沒有設置  }

如果sk2(即已bind的socket)是TCP_LISTEN狀態或者,sk2和新sk兩者都沒有設置_REUSEADDR的時候,可以判斷為衝突。

我們可以得出,如果原sock和新sock都設置了SO_REUSEADDR的時候,只要原sock不是Listen狀態,都可以綁定成功,甚至ESTABLISHED狀態也可以! 


這個在我們平常工作中,最常見的就是原sock處於TIME_WAIT狀態,這通常在我們關閉Server的時候出現,如果不設置SO_REUSEADDR,則會綁定失敗,進而啓動不來服務。而設置了SO_REUSEADDR,由於不是TCP_LISTEN,所以可以成功。 


這個特性在緊急重啓以及線下調試的非常有用,建議開啓。

SO_REUSEPORT

SO_REUSEPORT是Linux在3.9版本引入的新功能。

  1.在海量高併發連接的創建時候,由於正常的模型是單線程listener分發,無法利用多核優勢,這就會成為瓶頸。  2.CPU緩存行丟失

我們看下一般的Reactor線程模型, 


明顯的其單線程listen/accept會存在瓶頸(如果採用多線程epoll accept,則會驚羣,加WQ_FLAG_EXCLUSIVE可以解決一部分),尤其是在採用短鏈接的情況下。
鑑於此,Linux增加了SO_REUSEPORT,而之前bind中判斷是否衝突的下面代碼也是為這個參數而添加的邏輯:

  if(!reuseport || !sk2->sk_reuseport ||  			    (sk2->sk_state != TCP_TIME_WAIT &&  			     !uid_eq(uid, sock_i_uid(sk2))

這段代碼讓我們在多次bind的時候,如果設置了SO_REUSEPORT的時候不會報錯,也就是讓我們有個多線程(進程)bind/listen的能力。如下圖所示: 


而開啓了SO_REUSEPORT後,代碼棧如下:

  tcp_v4_rcv  	|->__inet_lookup_skb   		|->__inet_lookup  			|->__inet_lookup_listener   /* 用打分和偽隨機數等挑選出一個listen的sock */  struct sock *__inet_lookup_listener(......)  {  	......  	if (score > hiscore) {  			result = sk;  			hiscore = score;  			reuseport = sk->sk_reuseport;  			if (reuseport) {  				phash = inet_ehashfn(net, daddr, hnum,  						     saddr, sport);  				matches = 1;  			}  		} else if (score == hiscore && reuseport) {  			matches++;  			if (((u64)phash * matches) >> 32 == 0)  				result = sk;  			phash = next_pseudo_random32(phash);  		}  	......  }

直接在內核層面做負載均衡,將accept的任務分散到不同的線程的不同socket上(Sharding),毫無疑問可以多核能力,大幅提升連接成功後的socket分發能力。

Nginx已經採用SO_REUSEPORT

Nginx在1.9.1版本的時候引入了SO_REUSEPORT,配置如下:

  http {       server {            listen 80 reuseport;            server_name  localhost;            # ...       }  }    stream {       server {            listen 12345 reuseport;            # ...       }  }  

 

總結

Linux內核源碼博大精深,一個看起來簡單的bind系統調用竟然牽涉這麼多,在裏面可以挖掘出各種細節。在此分享出來,希望對讀者有所幫助。
編輯:hfy

收藏 人收藏
分享:

評論

相關推薦

谷歌和英特爾警告Linux內核都存在高嚴重性藍牙漏洞

谷歌和英特爾警告説,除了最新版本的Linux內核外,其他所有版本的Linux內核都存在高嚴重性藍牙漏....
的頭像 電子魔法師 發表於 10-16 17:00 323次 閲讀
谷歌和英特爾警告Linux內核都存在高嚴重性藍牙漏洞

一篇瞭解 Linux 操作系統需要仔細研讀的一篇文章

Linux 簡介 UNIX 是一個交互式系統,用於同時處理多進程和多用户同時在線。為什麼要説 UNI....
的頭像 Linux愛好者 發表於 10-14 14:02 345次 閲讀
一篇瞭解 Linux 操作系統需要仔細研讀的一篇文章

Linux閲碼場原創精華文章分享,你值得擁有

Linux學習方法: 宋寶華:迭代螺旋法關於Linux學習方法的血淚建議 宋寶華: 紀念金庸先生程序....
的頭像 Linuxer 發表於 10-10 16:28 269次 閲讀
Linux閲碼場原創精華文章分享,你值得擁有

揭開Linux內核進程上下文切換的神祕面紗

作者簡介 韓傳華,就職於南京大魚半導體有限公司,主要從事linux相關係統軟件開發工作,負責Soc芯....
的頭像 Linuxer 發表於 10-10 16:25 192次 閲讀
揭開Linux內核進程上下文切換的神祕面紗

linux內核參數設置_linux內核的功能有哪些

本文主要闡述了linux內核參數設置及linux內核的功能。
發表於 09-17 14:40 205次 閲讀
linux內核參數設置_linux內核的功能有哪些

linux內核是什麼_linux內核學習路線

Linux內核是一個操作系統(OS)內核,本質上定義為類Unix。它用於不同的操作系統,主要是以不同....
發表於 09-16 15:49 140次 閲讀
linux內核是什麼_linux內核學習路線

Linux內核的發展史

1991 年,21 歲的芬蘭大學生 Linus Torvalds 寫下第一行 Linux 內核代碼時....
的頭像 Linux愛好者 發表於 09-15 14:07 473次 閲讀
Linux內核的發展史

紅帽宣佈了其他容器堆棧功能

因此,IBM將Red Hat的OpenShift平台作為其混合雲戰略的核心。該公司上週表示,超過2,....
的頭像 倩倩 發表於 09-10 13:53 375次 閲讀
紅帽宣佈了其他容器堆棧功能

Linux內核的100%自由版本GNU Linux-libre 5.8發佈

開發團隊表示,此次清理的新驅動包括 Atom ISP Video、MediaTek 7663 USB....
的頭像 Linux愛好者 發表於 08-14 16:13 369次 閲讀
Linux內核的100%自由版本GNU Linux-libre 5.8發佈

乾貨:Linux內核中等待隊列的四個用法

Linux內核裏的等待隊列機制在做驅動開發時用的非常多,多用來實現阻塞式訪問,下面簡單總結了等待隊列....
的頭像 如意 發表於 06-20 09:59 415次 閲讀
乾貨:Linux內核中等待隊列的四個用法

深入linux內核架構 Linux內核架構分析解讀

概述 通常地,Linux操作系統如下圖所示,由四大子系統組成: 用户應用層: 特定Linux系統上使....
發表於 05-09 11:52 1111次 閲讀
深入linux內核架構 Linux內核架構分析解讀

Linux內核完全註釋修正版V3.0 帶目錄

發表於 01-17 19:40 265次 閲讀
Linux內核完全註釋修正版V3.0 帶目錄

使用C#和SQL SERVER數據庫實現圖書管理系統的詳細資料説明

本文檔的主要內容詳細介紹的是使用C#和SQL SERVER數據庫實現圖書管理系統的詳細資料説明。
發表於 01-02 08:00 170次 閲讀
使用C#和SQL SERVER數據庫實現圖書管理系統的詳細資料説明

頁面之間如何進行傳值詳細方法

本文檔的主要內容詳細介紹的是頁面之間如何進行傳值詳細方法。
發表於 10-23 17:20 173次 閲讀
頁面之間如何進行傳值詳細方法

網絡通信實驗無法重新連接該怎麼解決?

板子用client端,電腦用server端,連接上後服務端再斷開-重連,是正常的.但是當板子給電腦發送數據的過程中電腦服務端斷開,此時...
發表於 10-20 22:27 175次 閲讀
網絡通信實驗無法重新連接該怎麼解決?

使用SQL Server連接字符串的資料總結

以下的文章主要是介紹SQL Server連接字符串的總結,你如果是SQL Server連接字符串的瘋....
發表於 10-18 11:55 222次 閲讀
使用SQL Server連接字符串的資料總結

SQL-Server用户授權管理的教程免費下載

本文檔的主要內容詳細介紹的是SQL-Server用户授權管理的教程免費下載。 一.準備工作 1.....
發表於 10-15 11:41 204次 閲讀
SQL-Server用户授權管理的教程免費下載

ble client端給server寫數據速度慢該怎麼辦?

我用主機做client給從機通過GATT_WriteCharValue透傳一些數據,發現2s才發送一次,一次20字節,該怎麼解決?...
發表於 10-10 08:43 192次 閲讀
ble client端給server寫數據速度慢該怎麼辦?

如何才能將ACCESS遷移到SQL Server詳細經驗分析

前幾天,人很無聊,在同學的建議下用動網建了一個論壇,沒想到訪問人數一增加就不能進去,刷新也沒有用,很....
發表於 09-30 16:17 226次 閲讀
如何才能將ACCESS遷移到SQL Server詳細經驗分析

為什麼server和client必須要在同一個網段才能通信?

額,小弟最近在看lwip,有個問題一直困擾者我.為什麼server和client必須要在同一個網段才能通信呢? 如下是小弟的理解(以單片機作為...
發表於 09-29 04:51 772次 閲讀
為什麼server和client必須要在同一個網段才能通信?

進行LabVIEW和SQL SerVer數據庫之間的互訪方法説明

針對LabⅥEW在與專業數據庫的連接、數據操作等工作不易實現的不足,根據LabVmW 測試系統數據處....
發表於 09-26 08:00 279次 閲讀
進行LabVIEW和SQL SerVer數據庫之間的互訪方法説明

為什麼Altium17啓動總是很慢很慢?

每次都卡在這個界面好幾分鐘,starting integrated library server ,有哪位用過的嗎? ...
發表於 09-02 19:05 3751次 閲讀
為什麼Altium17啓動總是很慢很慢?

請問F407網絡通信實驗中網絡調試助手錯誤該怎麼辦?

用的紅龍F407的板子和它的網絡例程TCP Server測試時候,連接不上:錯誤顯示為connect() failed:socket is marked as no.......
發表於 09-02 04:36 224次 閲讀
請問F407網絡通信實驗中網絡調試助手錯誤該怎麼辦?

web server中網頁製作的軟件叫什麼?

web server中網頁製作的軟件叫什麼名?光盤中有嗎?謝謝...
發表於 08-22 01:53 533次 閲讀
web server中網頁製作的軟件叫什麼?

為什麼ucosII + lwip使用tcp作為server運行一段時間後會出現以下錯誤?

Assertion "tcpip_thread: invalid message" failed at line 146 in ..\..\source\plat\os\ucosII\lwip\lwip-1.4.1\src\api\t...
發表於 07-23 04:35 259次 閲讀
為什麼ucosII + lwip使用tcp作為server運行一段時間後會出現以下錯誤?

【集運王香港】linux 瞭解內核模塊的原理 《Rice linux 學習開發》

Linux內核是整體性結構,各個子系統緊密聯繫,上接用户控件,下接硬件,作為一個大程序在內核控件運行。 如果將所有的設備驅動...
發表於 07-16 07:00 376次 閲讀
【集運王香港】linux 瞭解內核模塊的原理 《Rice linux 學習開發》

怎麼才能打開server?

是要開啓了才能給esp8266發AT+CIPSTART="TCP","IP",8080對吧 嗚嗚嗚嗚 怎麼才能打開server啊 ...
發表於 06-18 01:16 61次 閲讀
怎麼才能打開server?

驅動之路-內核鏈表的使用

kernel list展示的是內核鏈表的結構,normallist展示的是普通鏈表的結構。head是....
發表於 05-15 17:24 337次 閲讀
驅動之路-內核鏈表的使用

微軟構建內部定製Linux內核 顯著提高Windows中微軟Linux子系統的性能

在微軟Build 2019開發者大會的第一天,微軟透露了其已經構建了一個內部定製的Linux內核,它....
的頭像 集運王香港網工程師 發表於 05-08 15:43 1923次 閲讀
微軟構建內部定製Linux內核 顯著提高Windows中微軟Linux子系統的性能

PHP教程之SERVER的詳細參數整理

PHP編程中經常需要用到一些服務器的一些資料,特把$_SERVER的詳細參數整理下,方便以後使用。
發表於 03-26 13:51 203次 閲讀
PHP教程之SERVER的詳細參數整理

VB程序設計電子教程之數據庫編程的詳細資料説明

本文檔詳細介紹的是VB程序設計電子教程之數據庫編程的詳細資料説明主要內容包括了:1.數據庫相關知識 ....
發表於 03-01 11:01 450次 閲讀
VB程序設計電子教程之數據庫編程的詳細資料説明

數據庫教程之SQL Server數據庫管理的詳細資料説明

本文檔詳細介紹的是數據庫教程之SQL Server數據庫管理的詳細資料説明主要內容包括了:1.瞭解S....
發表於 03-01 11:00 317次 閲讀
數據庫教程之SQL Server數據庫管理的詳細資料説明

數據庫設計開發技術案例教程之事務控制與鎖定

本文檔的主要內容詳細介紹的是數據庫設計開發技術案例教程之事務控制與鎖定主要內容包括了:1,事務的概念....
發表於 01-11 11:20 447次 閲讀
數據庫設計開發技術案例教程之事務控制與鎖定

數據庫設計開發技術案例教程之SQL Server權限與安全資料説明

本文檔的主要內容詳細介紹的是數據庫設計開發技術案例教程之SQL Server權限與安全資料説明主要內....
發表於 01-11 11:20 293次 閲讀
數據庫設計開發技術案例教程之SQL Server權限與安全資料説明

基於代理方式的有MySQL Proxy和Amoeba

Sharding的基本思想就要把一個數據庫切分成多個部分放到不同的數據庫(server)上,從而緩解....
的頭像 集運王香港網工程師 發表於 01-10 15:21 3440次 閲讀
基於代理方式的有MySQL Proxy和Amoeba

SQL Server 2005數據庫的應用手冊

SQL Server是基於服務器端的中型的數據庫,可以適合大容量數據的應用,在功能上管理上要比Acc....
發表於 01-10 08:00 190次 閲讀
SQL Server 2005數據庫的應用手冊

一文詳解Linux內核測試現狀

新的內核總是會定期發佈出來,但是其實大家並不是十分了解內核是如何被深入測試的。那麼這裏可以提前告訴大....
的頭像 Linuxer 發表於 01-01 09:06 1502次 閲讀
一文詳解Linux內核測試現狀

數據庫教程之SQL SERVER環境的詳細資料説明

本文檔的主要內容詳細介紹的是數據庫教程之SQL SERVER環境的詳細資料説明主要內容包括了:1 S....
發表於 12-18 15:07 199次 閲讀
數據庫教程之SQL SERVER環境的詳細資料説明

Windows Server 2012服務器管理器的詳細資料講解

在Windows Server 2012中服務器管理器發生了非常大的變化,在諸多方面做了非常大的改進....
發表於 11-29 11:47 888次 閲讀
Windows Server 2012服務器管理器的詳細資料講解

數據庫教程之數據庫的創建與管理詳細資料免費下載

本文檔的主要內容詳細介紹的是數據庫教程之數據庫的創建與管理詳細資料免費下載。內容包括了:SQL Se....
發表於 10-19 10:41 196次 閲讀
數據庫教程之數據庫的創建與管理詳細資料免費下載

一文詳解Linux內核的棧回溯與妙用

網上或多或少都能找到棧回溯的一些文章,但是講的都並不完整,沒有將內核棧回溯的功能用於實際的內核、應用....
的頭像 Linuxer 發表於 10-05 10:02 2655次 閲讀
一文詳解Linux內核的棧回溯與妙用

如何在眾多Linux內核版本中選擇最適合你最穩當的一個版本?

Linux Kernel 的穩定分支維護者 Greg Kroah-Hartman 近日在其個人博客上....
的頭像 Linux愛好者 發表於 09-01 08:59 3741次 閲讀
如何在眾多Linux內核版本中選擇最適合你最穩當的一個版本?

Linux內核的裁剪以及移植過程的基本原理和詳細方法資料概述

微處理器的產生為價格低廉、結構小巧的CPU和外設的連接提供了穩定可靠的硬件架構,這樣,限制嵌入式系統....
發表於 08-31 15:18 1383次 閲讀
Linux內核的裁剪以及移植過程的基本原理和詳細方法資料概述

關於Linux內存模型的介紹

在linux內核中支持3中內存模型,分別是flat memory model,Discontiguo....
的頭像 Linuxer 發表於 07-18 16:26 2247次 閲讀
關於Linux內存模型的介紹

Linux內核的DL調度器的細節和怎麼樣使用DL調度器?

Linux內核的DL調度器是一個全局EDF調度器,它主要針對有deadline限制的sporadic....
的頭像 Linuxer 發表於 07-16 10:54 2765次 閲讀
Linux內核的DL調度器的細節和怎麼樣使用DL調度器?

嵌入式C語言的三道關鍵性試題和答案你知道嗎?

簡述ARM Linux內核啓動三個階段的功能。 在嵌入式系統中對GUI的基本要求是什麼? ARM....
的頭像 嵌入式ARM 發表於 07-06 10:09 2985次 閲讀
嵌入式C語言的三道關鍵性試題和答案你知道嗎?

數據庫原理實驗指導書之SQL_Server_2005

本文主要介紹了數據庫原理實驗指導書之SQL_Server_2005.
發表於 06-27 08:00 230次 閲讀
數據庫原理實驗指導書之SQL_Server_2005

ARM處理器上的linux內核啓動的過程詳細資料概述

對於ARM的處理器,內核第一個啓動的文件是arc/arm/kernel下面的head.S文件。當然a....
的頭像 21ic電子網 發表於 06-10 11:03 2237次 閲讀
ARM處理器上的linux內核啓動的過程詳細資料概述

世界還沒有準備好迎接Linux 5.0,Linux 4.17內核發佈

Torvalds再一次“戲弄”了命名法,他表示,世界還沒有為Linux 5.0準備好,所以才有了4.....
的頭像 Linux愛好者 發表於 06-06 09:14 1739次 閲讀
世界還沒有準備好迎接Linux 5.0,Linux 4.17內核發佈

如何自行編譯一個Linux內核的詳細資料概述

曾經有一段時間,升級 Linux 內核讓很多用户打心裏有所畏懼。在那個時候,升級內核包含了很多步驟,....
的頭像 Linux愛好者 發表於 05-27 10:12 1585次 閲讀
如何自行編譯一個Linux內核的詳細資料概述

微軟向物聯網靠近 定製 Linux內核版問世

開放還是封閉這對微軟曾經是一個問題,但後來,微軟一次又一次向開源靠攏,像是兩條腿走路,穩固原有的商業....
發表於 04-24 15:03 342次 閲讀
微軟向物聯網靠近 定製 Linux內核版問世

如何構建達芬奇的DSP Server詳細中文概述

 德州儀器(T I)的達芬奇(DaVinCi)力數字媒體技術平台包括四大部分: 芯片(處理器)、開發....
發表於 04-23 09:37 332次 閲讀
如何構建達芬奇的DSP Server詳細中文概述

Linux內核源代碼情景分析(全冊高清帶書籤)pdf下載

Linux內核源代碼情景分析需要的拿走吧
發表於 01-04 16:57 422次 閲讀
Linux內核源代碼情景分析(全冊高清帶書籤)pdf下載

Linux DNS 服務器安裝、配置和維護的詳細解析

每個 IP 地址都可以有一個主機名,主機名由一個或多個字符串組成,字符串之間用小數點隔開。有了主機名....
的頭像 馬哥Linux運維 發表於 12-18 15:08 5584次 閲讀
Linux DNS 服務器安裝、配置和維護的詳細解析

SQL Server遊標語句的使用方法介紹

  遊標屬於行級操作 消耗很大 SQL查詢是基於數據集的所以一般查詢能有 能用數據集 就用數據集 別....
發表於 11-29 09:08 1779次 閲讀
SQL Server遊標語句的使用方法介紹

SQL Server數據庫學習總結

經過一段時間的學習,也對數據庫有了一些認識。數據庫基本是由表,關係,操作組成;對於初學者首先要學的:....
發表於 11-28 17:36 3272次 閲讀
SQL Server數據庫學習總結

server內部異常堆棧跟蹤的結尾

現在項目需求是這樣的:客户是做直銷行業的,現在他們用着幾個軟件系統,我們稱之為業務系統,假設為A,B....
發表於 11-28 16:16 4204次 閲讀
server內部異常堆棧跟蹤的結尾

linux內核無法啓動

 Linux在啓動過程中會出現一些故障,導致系統無法正常啓動,本文列舉了幾個應用單用户模式、GRUB....
發表於 11-14 17:26 918次 閲讀
linux內核無法啓動

linux內核啓動參數設置

name”是關鍵字,內核用它來識別應該把“關鍵字”後面的值傳遞給誰,也就是如何處理這個值,是傳遞給處....
發表於 11-14 16:50 965次 閲讀
linux內核啓動參數設置

linux內核啓動流程

Linux的啓動代碼真的挺大,從彙編到C,從Makefile到LDS文件,需要理解的東西很多。畢竟L....
發表於 11-14 16:19 1992次 閲讀
linux內核啓動流程