linux c程式設計 程序程式設計(整理)
(程式碼來自《嵌入式linux應用程式開發標準教程》)
概覽:
第一部份:程序簡介
第二部份:程序控制 :命令 函式
第三部份:程序例項: 多程序 守護程序
第四部份:附加材料
linux 程序控制函式大全
第一部份:程序簡介
程序是Linux系統的基本排程和管理資源的單位,它是通過程序控制塊來描述的。程序控制塊包含了程序的描述資訊、控制資訊以及資源資訊,它是程序的一個靜態描述。在Linux中,程序控制塊中的每一項都是一個task_struct結構。
在Linux中最主要的程序標識有程序號(PID,Process Idenity Number)和它的父程序號(PPID,parent process ID)。其中PID惟一地標識一個程序。PID和PPID都是非零的正整數。
在Linux中獲得當前程序的PID和PPID的系統呼叫函式為getpid()和getppid(),通常程式獲得當前程序的PID和PPID之後,可以將其寫入日誌檔案以做備份。
另外,程序標識還有使用者和使用者組標識、程序時間、資源利用情況等
程序是Linux系統的基本排程和管理資源的單位,它是通過程序控制塊來描述的。程序控制塊包含了程序的描述資訊、控制資訊以及資源資訊,它是程序的一個靜態描述。在Linux中,程序控制塊中的每一項都是一個task_struct結構。
在Linux中最主要的程序標識有程序號(PID,Process Idenity Number)和它的父程序號(PPID,parent process ID)。其中PID惟一地標識一個程序。PID和PPID都是非零的正整數。
在Linux中獲得當前程序的PID和PPID的系統呼叫函式為getpid()和getppid(),通常程式獲得當前程序的PID和PPID之後,可以將其寫入日誌檔案以做備份。
另外,程序標識還有使用者和使用者組標識、程序時間、資源利用情況等
程序三種狀態 就緒 執行 等待
第二部份:程序控制
常用命令
-
at命令:在指定時刻執行指定的命令序列
格式:
at [-V] [-q x] [-f file] [-m] time
atq [-V] [-q x]
atrm [-V] [-q x] job…
batch [-V] [-f file] [-m]
-
bg命令:使一個被掛起的程序在後臺執行
格式:bg 該命令無引數。
先使用組合鍵"Ctrl+Z"。然後使用bg命令。如果想直接把這個命令放在後臺執行,可以在命令後使用"&"符號:
#du -a / | sort -rn > /tmp/du.sorted &
-
fg命令:使一個被掛起的程序在前臺執行
格式:fg -[job-spec]
-
jobs命令:顯示後臺任務的執行情況
格式:jobs [選項] [jobspec…]
-
kill命令:終止一個程序
格式:kill [-s signal |-p] [-a]pid
-
crontab命令:用於安裝、刪除或者列出用於驅動cron後臺程序的任務表。然後,該配置由cron守護程序在設定的時間執行
格式:crontab [-u user] 檔案
-
ps命令:檢視系統中程序的狀態
格式:ps [選項],如ps aux
-
pstree命令:列出當前的程序,以及它們的樹狀結構
格式:pstree [選項] [pid|user]
-
top命令:顯示系統當前的程序狀況
格式:top [選項]
說明:top命令和ps命令的基本作用是相同的,都顯示系統當前的程序狀況。但是top是一個動態顯示過程,即可以通過使用者按鍵來不斷重新整理當前狀態。
-
nice命令:改變程式執行的優先權等級
格式:nice [-n <優先等級>][--help][--version][命令]
說明:應用程式優先權值的範圍從-20~19,數字越小,優先權就越高。一般情況下,普通應用程式的優先權值(CPU使用權值)都是0,如果讓常用程式擁有較高的優先權等級,自然啟動和執行速度都會快些。需要注意的是普通使用者只能在0~19之間調整應用程式的優先權值,只有超級使用者有權調整更高的優先權值(從-20~19)。
-
renice命令:允許使用者修改一個正在執行的程序的優先權
格式:renice priority [ [ -p ] pids ] [ [ -g ] pgrps ] [ [ -u ] users ]
說明:renice命令可重新調整正在執行的程式的優先權等級。預設是以程式識別碼指定程式,調整其優先權,也可以指定程式群組或使用者名稱稱調整優先權等級,並修改所有隸屬於該程式群組或使用者的程式的優先權。等級範圍從-20~19,只有超級使用者可以改變其他使用者程式的優先權和設定負數等級。普通使用者只能對自己所有的程序使用renice命令。
-
sleep命令:使程序暫停執行一段時間
格式:sleep number [選項]
-
nohup命令:使用者退出系統之後繼續工作
格式:nohup命令
說明:一般退出Linux系統時,會把所有的程式全部結束掉,包括那些後臺程式。但有時候,例如,使用者正在下載一個很大的檔案,但是你因下班或有事需要先退出系統,希望退出系統時程式還能繼續執行。這時,我們就可以使用nohup命令使程序在使用者退出後仍繼續執行。同時這些程序都在後臺執行(命令放到後臺執行,nohup必須與&操作同時使用),結果則會寫到使用者自己的目錄下的nohup.out檔案裡。
-
pgrep命令:查詢當前執行的程序,並列出匹配給定條件的程序的pid,所有的條件都必須匹配才會被列出
格式:pgrep [選項][程式名]
-
chkconfig命令: 檢查,設定系統的各種服務
格式:chkconfig [--add][--del][--list][系統服務]
獲取程序id
Linux程序的管理 <一>獲取程序資訊函式
程序又稱任務,是一個動態的使用系統資源、處於活動狀態的應用程式。
程序的管理由程序控制塊PCB、程序排程、中斷管理、任務佇列等組成,它是linux檔案系統、儲存管理、裝置管理和驅動程式的基礎。
程序控制塊PCB中包含了程序的所有資訊,主要包括程序PID、程序所佔有的記憶體區域、檔案描述符和程序環境等資訊。
他用task_struct的資料結構表示,存在於include/linux/sch.h
程序狀態及轉換
#define TASK_RUNNING 0 //執行狀態
#define TASK_INTERRUPTIBLE 1 //等待狀態(可被中斷)
#define TASK_UNINTERRUPTIBLE 2 //等待狀態(不可被中斷)
#define TASK_STOPPED 4 //停止狀態
#define TASK_ZOMBIE 8 //睡眠狀態
#define TASK_DEAD 16 //僵死狀態
程序的基本操作,六大類:
1.獲取程序資訊函式:主要通過讀取程序控制塊PCB中的資訊。
(1)getpid()
功能:用來獲取目前程序的程序標識。
定義函式:pid_t getpid(void)
返回值:返回當前程序的程序識別號。
標頭檔案:#include <unistd.h>
(2)getppid()
功能:用來獲取目前程序的父程序標識。
定義函式:pid_t getppid(void)
返回值:返回當前程序的父程序識別號。
標頭檔案:#include <unistd.h>
(3)getpgid()
功能:用來獲得引數pid指令程序所屬於的組識別號,若引數為0,則返回當前程序的組識別碼。
定義函式:pid_t getpgid(pid_t pid)
返回值:執行成功則返回正確的組識別碼,若有錯則返-1,錯誤原因存在於errno中。
標頭檔案:#include <unistd.h>
(4)getpgrp()
功能:用來獲得目前程序所屬於的組識別號,等價於getpgid(0)。
定義函式:pid_t getpgrp(void)
返回值:執行成功則返回正確的組識別碼。
標頭檔案:#include <unistd.h>
(5)getpriotity(void)
功能:用來獲得程序,程序組和使用者的程序執行優先權。
定義函式:int getpriority(int which,int who)
引數含義:
which:
PRIO_PROCESS who為程序的識別碼
PRIO_PGRP who為程序的組識別碼
PRIO_USER who為使用者識別碼
返回值:執行成功則返回當前程序的優先順序(-20--20),值越小優先順序越高。若出錯則返-1,原因在errno中。
標頭檔案:#include <sys/resource.h>
簡單例項:
[[email protected] systemCall]$ cat -n get_process_information.c
1 #include <stdio.h>
2 #include <unistd.h>
3 #include <sys/resource.h>
4
5 int main(/*int argc,char **argv*/)
6 {
7 printf("This process's pid is:%d",getpid());
8 printf("/nThis process's farther pid is:%d",getppid());
9 printf("/nThis process's group pid is:%d",getpgid(getpid()));
10 printf("/nThis process's group pid is:%d",getpgrp());
11 printf("/nThis process's priority is:%d/n",getpriority(PRIO_PROCESS,getpid()));
12 return 0;
13 }
[[email protected] systemCall]$ ./get_process_information
This process's pid is:6172
This process's farther pid is:5681
This process's group pid is:6172
This process's group pid is:6172
This process's priority is:0
[[email protected] systemCall]$
程序控制函式
程序函式-獲取程序ID
pid_t getpid(void)功能:獲取本程序ID
pid_t getppid(void)功能:獲取父程序ID
程序函式-建立子程序
pid_t fork(void)功能:建立子程序
fork會被呼叫一次,卻返回兩次,有三種不同的返回值:
1.在父程序中,fork返回子程序建立的PID.
2.在子程序中,fork返回0.
3.如果出現錯誤,fork返回一個負值.
注:子程序會複製程式碼自行執行,子程序中的變數不影響父程序,子程序執行的次序不確定.
pid_t vfork(void)功能:建立子程序
vfork會被呼叫一次,卻返回兩次,有三種不同的返回值:
1.在父程序中,vfork返回子程序建立的PID.
2.在子程序中,vfork返回0.
3.如果出現錯誤,vfork返回一個負值.
注:子程序與父程序共享資料段,子程序中的變數與父程序保持一致,子程序比父程序優先執行.
程序函式-exec函式
注:exec函式啟動一個新的程式,會替換原有的程序,因此程序的PID保持不變.
int execl(const char * path , const char * arg1 , ...)
變數 | 作用 |
---|---|
path | 被執行程式名(含完整路徑) |
arg1 - argn | 被執行程式所需的命令列引數,含程式名.以空指標(NULL)結束. |
int execlp(const char * path , const char * arg1 , ...)
變數 | 作用 |
---|---|
path | 被執行的程式名(不含路徑,將從PATH環境變數中查詢該程式) |
arg1 - argn | 被執行程式所需的命令列引數,含程式名.以空指標(NULL)結束. |
int execv(const char * path , char * const argv[])
變數 | 作用 |
---|---|
path | 被執行程式名(含完整路徑) |
argv[ ] | 被執行程式所需要的命令列引數陣列. |
int system(const char* string)功能:呼叫fork產生子程序,由子程序呼叫"/bin/sh -c string"來執行引數string所代表的命令與引數.
程序函式-程序等待
pid_t wait(int * status)功能:阻塞該程序,直到其某個子程序退出.
int pause(void)功能:pause只有在執行了一個訊號處理程式並從其返回時,pause才返回. 守護程序 五步走+出錯處理 1,建立子程序,父程序退出 2,setsid() 3,切換目錄 4,umask 5,釋放檔案資源 出錯處理syslog openlog closelog
第三部份:程序程式設計例項
多程序例項
/* multi_proc.c */
#include <stdio.h>
#include <stdlib.h>
#include <sys/types.h>
#include <unistd.h>
#include <sys/wait.h>
int main(void)
{
pid_t child1, child2, child;
/*ŽŽœšÁœžö×Óœø³Ì*/
child1 = fork();
/*×Óœø³Ì1µÄ³öŽíŽŠÀí*/
if (child1 == -1)
{
printf("Child1 fork error\n");
exit(1);
}
else if (child1 == 0) /*ÔÚ×Óœø³Ì1Öе÷ÓÃexeclpº¯Êý*/
{
printf("In child1: execute 'ls -l'\n");
if (execlp("ls", "ls", "-l", NULL) < 0)
{
printf("Child1 execlp error\n");
}
}
else /*ÔÚžžœø³ÌÖеȎý×Óœø³Ì2µÄÍ˳ö*/
{
child2 = fork();
if (child2 == -1) /*×Óœø³Ì2µÄ³öŽíŽŠÀí*/
{
printf("Child2 fork error\n");
exit(1);
}
else if( child2 == 0 ) /*ÔÚ×Óœø³Ì2ÖÐʹÆäÔÝÍ£5s*/
{
printf("In child2: sleep for 5 seconds and then exit\n");
sleep(5);
exit(0);
}
printf("In father process:\n");
child = waitpid(child1, NULL, 0);
if (child == child1)
{
printf("Get child1 exit code\n");
}
else
{
printf("Error occured!\n");
}
do
{
child = waitpid(child2, NULL, WNOHANG );
if (child == 0)
{
printf("The child2 process has not exited!\n");
sleep(1);
}
} while (child == 0);
if (child == child2)
{
printf("Get child2 exit code\n");
}
else
{
printf("Error occured!\n");
}
}
exit(0);
}
守護程序例項
/* daemon_proc.c */ #include <stdio.h> #include <stdlib.h> #include <sys/types.h> #include <unistd.h> #include <sys/wait.h> #include <syslog.h> int main(void) { pid_t child1,child2; int i; /*建立子程序1*/ child1 = fork(); if (child1 == 1) { perror("child1 fork"); exit(1); } else if (child1 > 0) { exit(0); } /*開啟日誌服務*/ openlog("daemon_proc_info", LOG_PID, LOG_DAEMON); /*以下幾步是編寫守護程序的常規步驟*/ setsid(); chdir("/"); umask(0); for(i = 0; i < getdtablesize(); i++) { close(i); } /*建立子程序2*/ child2 = fork(); if (child2 == 1) { perror("child2 fork"); exit(1); } else if (child2 == 0) { /*在日誌中寫入字串*/ syslog(LOG_INFO, " child2 will sleep for 10s "); sleep(10); syslog(LOG_INFO, " child2 is going to exit! "); exit(0); } else { waitpid(child2, NULL, 0); syslog(LOG_INFO, " child1 noticed that child2 has exited "); /*關閉日誌服務*/ closelog(); while(1) { sleep(10); } } }
相關推薦
Linux-C成長之路(九)Linux C程式設計實戰之路 複合資料型別
Linux C程式設計實戰之路 複合資料型別 咱們知道,C語言中有許多基本資料型別,比如int型,float型,double型等,我們經常使用這些基本資料型別來表達一些簡單的資料,比如一個人的年齡可以用 int 型資料來表示,一本書的價格可以用 float 型
C語言程序設計(基礎)最後一次作業-- 總結報告
人際關系 領域 健康 作用 每次 收獲 會有 做出 理解 一、總體總結 1、當初你是如何做出選擇計算機專業的決定的?經過一個學期,你的看法改變了麽,為什麽? 你覺得計算機是你喜歡的領域嗎,它是你擅長的領域嗎? 為什麽? 當初填報誌願時,是我自己選擇的計算機專業,同時也采取
C++ vector的用法(整理)
vector 是向量型別,它可以容納許多型別的資料,如若干個整數,所以稱其為容器。vector 是C++ STL的一個重要成員,使用它時需要包含標頭檔案: #include<vector>; 一、vector 的初始化:可以有五種方式,舉例說明如下: (1) vector&
Linux應用快捷鍵彙集(整理)
原文地址:http://blog.chinaunix.net/uid-21123336-id-1830510.html Gnome快捷鍵 通用快捷鍵 Alt + F1 類似Windows下的Win鍵,在GNOME中開啟"應用程式"選單(Applications) Alt +
Linux學習之程序通訊(一)
言之者無罪,聞之者足以戒。 ——《詩序》 ctrl+alt+t 開啟終端 一、程序間通訊和執行緒間通訊: 程序通訊:在使用者空間實現程序通訊是不可能的,通過Linux核心通訊 執行緒通訊:可以在使用者空間就可以實現,可以通過全域性變數通訊 二、通訊方式:
Linux學習之程序通訊(二)
言之者無罪,聞之者足以戒。 ——《詩序》 命令:kill -l 可以檢視核心可以傳送多少種訊號 命令:ps -axj 可以檢視程序的狀態 訊號: 訊號通訊,其實就是核心向用戶空間程序傳送訊號,只有核心才能發訊號,使用者空間程序不能傳送訊號 訊號通訊的框架: (
Linux學習之程序通訊(三)
言之者無罪,聞之者足以戒。 ——《詩序》 二、訊號的接收 接收訊號的程序,需要的條件:要想使接收的程序能收到訊號,這個程序就不能結束 接收訊號的函式:sleep()、while(1)、pause() sleep()函式使程序進入睡眠狀態(S) pause()函式使程
Linux學習之程序通訊(四)
言之者無罪,聞之者足以戒。 ——《詩序》 IPC通訊 IPC通訊有三種:共享記憶體、訊息佇列、訊號燈 這個IPC物件,是存在於核心中的。而且使用者空間的檔案系統中沒有IPC檔案型別 IPC物件 IPC和檔案IO函式的比較: 檔案I/O
Linux學習之程序通訊(五)
言之者無罪,聞之者足以戒。 ——《詩序》 訊息佇列: 鏈式佇列: msqid ds 維護訊息佇列的結構體,佇列的第一個訊息指標msg_first,最後一個訊息指標msg_last 訊息中有一個成員指標next 每一個訊息中包含有哪些內容: Data
linux c用open開啟(建立)一個檔案
1、檔案描述符 Linux作業系統核心(kernel)利用檔案描述符來訪問檔案,檔案描述符大於等於0,是一個使用者描述被開啟檔案的索引值,它指向該檔案的相關資訊記錄表,當檔案開啟或者建立新檔案的時,就會返回一個檔案描述符,當讀寫檔案時,也需要使用檔案描述符來指定特寫檔案。
Linux--C語言操作資料庫(一)插入資料
各種渠道去找有關於使用C語言操作資料庫的資料,好辛苦,弄出來了! 資料庫部分 首先建立一張表 create table children(childno int not null unique,fname varchar(20),age int);
linux 編寫守護程序例子 (Daemon)
例子如下 #include <stdio.h> #include <stdlib.h> #include <sys/types.h> #include <unistd.h> //fork int Daemon(void)
C++ set用法總結(整理)
順序容器包括vector、deque、list、forward_list、array、string,所有順序容器都提供了快速順序訪問元素的能力。 關聯容器包括set、map 關聯容器和順序容器有著根本的不同:關聯容器中的元素是按關鍵字來儲存和訪問的。與之相對,順序容器
Linux 筆試面試常見題目(整理)
一.填空題: 在Linux系統中,以 檔案 方式訪問裝置 。 Linux核心引導時,從檔案 /etc/fstab 中讀取要載入的檔案系統。 Linux檔案系統中每個檔案用 i節點 來標識。 全部磁碟塊由四個部分組成,分別為引導塊 、專用塊 、 i節點表塊 和
linux c程式設計 程序程式設計(整理)
(程式碼來自《嵌入式linux應用程式開發標準教程》) 概覽: 第一部份:程序簡介 第二部份:程序控制 :命令 函式 第三部份:程序例項: 多程序 守護程序 第四部份:附加材料 linux 程序控制函式大全 第一部份:程序簡介 程序是Lin
Linux C 之檔案程式設計(2)
read & write #read 從與檔案描述符 fd 相關的檔案中讀取 n bytes 個位元組的資料到 buf 中,返回實際讀入的位元組數; ##write 將字串 buf 中前 n bytes 個位元組的資料寫入與檔案描述符 fd 關聯的檔案中,
Linux C高階程式設計——網路程式設計之UDP(4)
Linux網路程式設計——UDP 宗旨:技術的學習是有限的,分享的精神是無限的。 下面分析一幀基於UDP的TFTP協議幀。 乙太網首部 0000: 00 05 5d 67 d0 b1 00 05 5d 61 58 a8 08 00 IP首部0000: 45 00 00
Linux C高階程式設計——網路程式設計之乙太網(2)
Linux網路程式設計——乙太網 宗旨:技術的學習是有限的,分享的精神是無限的。 1、乙太網幀格式 源地址和目的地址是指網絡卡的硬體地址(也叫MAC地址),長度是48位,是在網絡卡出廠時固化的。用ifconfig命令檢視,“ 硬體地址 00:0c:29
Linux C高階程式設計——網路程式設計之API(5)
Linux C網路程式設計——API 宗旨:技術的學習是有限的,分享的精神的無限的。 一、基本socket函式 Linux系統是通過提供套接字(socket)來進行網路程式設計的。網路的socket資料傳輸是一種特殊的I/O,socket也是一種檔案描述
Linux C高階程式設計——網路程式設計之TCP(3)
Linux網路程式設計(三)——TCP 宗旨:技術的學習是有限的,分享的精神是無限的。 1、TCP段格式 和UDP協議一樣也有源埠號和目的埠號,通訊的雙方由IP地址和埠號標識。32位序號、32位確認序號、視窗大小。4位首部長度和IP協議頭類似,表示TCP協議頭的長度,以4位元組為單位,