導航:首頁 > 源碼編譯 > 編譯器後端多線程

編譯器後端多線程

發布時間:2022-06-28 00:02:56

❶ C語言可以實現 中斷 和 多線程 這類功能嗎

「暈,C語言不是灰常強大,無所不能嗎?怎麼有人說C語言不能實現 中斷 和多線程??」這句話要分兩部分來說,首先「暈,C語言不是灰常強大,無所不能嗎?」。沒有任何一種語言可以無所不能,原因很簡單,任何的語言都脫離不了編譯工具,而編譯工具脫離不了編譯環境。由於編譯環境的不同,因此編譯工具也有所不同,有得只針對JAVA,有得指針對C++,有得只針對C#。不管C語言多厲害,如果編譯工具不支持,那也沒有辦法在這個編譯工具上編譯,以至於沒有辦法在那個編譯工具的編譯環境中運行。所以不能說無所不能。
「怎麼有人說C語言不能實現 中斷 和多線程啊」,這是一個概念性問題。純粹的C語言只是一個工具,更多的是一種定義,一種格式,可以抽象成一種風格。就像定義一個整型變數i。為什麼你不能用integer i定義,非得int i。例如函數的編寫形式,命名規則等等。假如按照C語言的這些規則來編寫程序,同時編譯工具支持C語言,提供中斷庫,還有多線程庫,那麼C語言同樣也可以實現中斷和多線程。舉個例子:例如你手頭上只有一個TC編譯工具,雖然他支持C語言,但是只能編譯16位的DOS程序,礙於這個編譯工具的局限性,所以你永遠也寫不出像Windows操作系統那種帶窗口界面的Win32程序,也不能寫一個針對.NET框架的網路服務程序。同樣的,假如你要開發一個Windows軟體,使用VC編譯器,而這個編譯工具本身帶多線程庫,同時支持Windows系統的很多調用,所以你完全可以以C語言的風格在這個編譯器中調用各種Win32 SDK,開發一個多線程的Windows應用程序。假如你要使用中斷,在Windows環境下可以使用微軟提供的DDK(驅動開發包),他同樣支持C語言,那麼你就可以通過這個開發包調用很多中斷。在linux環境下,不需要開發包就可以直接調用,因為Linux自帶了很多系統調用都是開放的。頭文件聲明直接就在Linux文件系統的Sys目錄下。所以說他僅僅是一種風格。依賴於編譯環境的系統調用同樣也依賴於編譯環境提供的鏈接庫。

❷ 編譯器如何處理多線程程序

這是一個多線程例子,裡面只有兩個線程,是生產者/消費者模式,已編譯通過,注釋很詳細,
如下:

/* 以生產者和消費者模型問題來闡述Linux線程的控制和通信你
生產者線程將生產的產品送入緩沖區,消費者線程則從中取出產品。
緩沖區有N個,是一個環形的緩沖池。
*/
#include <stdio.h>
#include <pthread.h>

#define BUFFER_SIZE 16

struct prodcons
{
int buffer[BUFFER_SIZE];/*實際存放數據的數組*/
pthread_mutex_t lock;/*互斥體lock,用於對緩沖區的互斥操作*/
int readpos,writepos; /*讀寫指針*/
pthread_cond_t notempty;/*緩沖區非空的條件變數*/
pthread_cond_t notfull;/*緩沖區未滿 的條件變數*/
};

/*初始化緩沖區*/
void pthread_init( struct prodcons *p)
{
pthread_mutex_init(&p->lock,NULL);
pthread_cond_init(&p->notempty,NULL);
pthread_cond_init(&p->notfull,NULL);
p->readpos = 0;
p->writepos = 0;
}

/*將產品放入緩沖區,這里是存入一個整數*/
void put(struct prodcons *p,int data)
{
pthread_mutex_lock(&p->lock);
/*等待緩沖區未滿*/
if((p->writepos +1)%BUFFER_SIZE ==p->readpos)
{
pthread_cond_wait(&p->notfull,&p->lock);
}
p->buffer[p->writepos] =data;
p->writepos++;
if(p->writepos >= BUFFER_SIZE)
p->writepos = 0;
pthread_cond_signal(&p->notempty);
pthread_mutex_unlock(&p->lock);
}
/*從緩沖區取出整數*/
int get(struct prodcons *p)
{
int data;
pthread_mutex_lock(&p->lock);
/*等待緩沖區非空*/
if(p->writepos == p->readpos)
{
pthread_cond_wait(&p->notempty ,&p->lock);//非空就設置條件變數notempty
}
/*讀書據,移動讀指針*/
data = p->buffer[p->readpos];
p->readpos++;
if(p->readpos == BUFFER_SIZE)
p->readpos = 0;
/*設置緩沖區未滿的條件變數*/
pthread_cond_signal(&p->notfull);
pthread_mutex_unlock(&p->lock);
return data;
}
/*測試:生產站線程將1 到1000的整數送入緩沖區,消費者線程從緩沖區中獲取整數,兩者都列印信息*/
#define OVER (-1)
struct prodcons buffer;
void *procer(void *data)
{
int n;
for( n=0;n<1000;n++)
{
printf("%d ------>\n",n);
put(&buffer,n);
}
put(&buffer,OVER);
return NULL;
}
void *consumer(void *data)
{
int d;
while(1)
{
d = get(&buffer);
if(d == OVER)
break;
else
printf("----->%d\n",d);
}
return NULL;
}
int main()
{
pthread_t th_p,th_c;
void *retval;
pthread_init(&buffer);
pthread_create(&th_p,NULL,procer,0);
pthread_create(&th_c,NULL,consumer,0);
/*等待兩個線程結束*/
pthread_join(th_p, &retval);
pthread_join(th_c,&retval);
return 0;
}

❸ c的多線程實現

像LINUX那種民間系統應該不會有CPU的優化指令,好多CPU都是針對WINDOWS優化的,只能說雙核處理多線程比單核要快一倍而已。

❹ C語言編譯器是否支持多線程

C語言編譯器有很多,只要不是太舊的都支持多線程。C語言本身是沒有多線程的概念的,都是操作系統提供支持,所以不同操作系統中的多線程實現起來可能完全不一樣。

❺ 如何讓makefile支持多線程

在Linux下編譯個多線程命令為:

gcc -lpthread -o file file.c

在Linux下用交叉編譯器編譯個在uc下運行多線程makefile文件如下:

CFLAGS = -Wall -Os -D -D__linux__ -Dunix -D__uClinux__ -DEMBED

LDFLAGS =-Wl,-elf2flt
LOCAL_LIBS = /usr/local/arm-elf/lib/libpthread.a

CC = arm-elf-gcc

LD = arm-elf-gcc

TARGT = test

OBJ = $(TARGT).o

SRC = $(TARGT).c

all: $(TARGT)

%.o:%.c

$(CC) $(CFLAGS) -c $< -o $@

$(TARGT) :$(OBJ) $(LOCAL_LIBS)

$(CC) $(CFLAGS) $(LDFLAGS) -o $@ $(OBJ) $(LOCAL_LIBS) $(LDLIBS)

clean:

-rm -f $(EXEC) *.elf *.gdb *.o

❻ gcc編譯線程程序,為什麼要加-lpthread,頭文件已經包含了<pthread.h>了啊

-lpthread是鏈接庫,

<pthread.h>只有申明,實現部分都在庫裡面。

創建線程時一般是把函數的指針做參數,所以要加一個取地址符號。

ret=pthread_create(&id,NULL,(void *)&thread,NULL);

另外,建議要檢查一下創建線程的返回值ret是否成功,防止影響後面的代碼。

(6)編譯器後端多線程擴展閱讀:

每個語言編譯器都是獨立程序,此程序可處理輸入的原始碼,並輸出組合語言碼。全部的語言編譯器都擁有共通的中介架構:一個前端解析符合此語言的原始碼,並產生一抽象語法樹,以及一翻譯此語法樹成為GCC的暫存器轉換語言〈RTL〉的後端。

編譯器最佳化與靜態程序碼解析技術(例如FORTIFY_SOURCE,一個試圖發現緩沖區溢位〈buffer overflow〉的編譯器)在此階段應用於程序碼上。最後,適用於此硬體架構的組合語言程序碼以Jack Davidson與Chris Fraser發明的演算法產出。

❼ 什麼是編譯器

編譯器

編譯器是一種特殊的程序,它可以把以特定編程語言寫成的程序變為機器可以運行的機器碼。我們把一個程序寫好,這時我們利用的環境是文本編輯器。這時我程序把程序稱為源程序。在此以後程序員可以運行相應的編譯器,通過指定需要編譯的文件的名稱就可以把相應的源文件(通過一個復雜的過程)轉化為機器碼了。

[編輯]編譯器工作方法
首先編譯器進行語法分析,也就是要把那些字元串分離出來。然後進行語義分析,就是把各個由語法分析分析出的語法單元的意義搞清楚。最後生成的是目標文件,我們也稱為obj文件。再經過鏈接器的鏈接就可以生成最後的可執行代碼了。有些時候我們需要把多個文件產生的目標文件進行鏈接,產生最後的代碼。我們把一過程稱為交叉鏈接。

一個現代編譯器的主要工作流程如下:

* 源程序(source code)→預處理器(preprocessor)→編譯器(compiler)→匯編程序(assembler)→目標程序(object code)→連接器(鏈接器,Linker)→可執行程序(executables)

工作原理

編譯是從源代碼(通常為高級語言)到能直接被計算機或虛擬機執行的目標代碼(通常為低級語言或機器言)。然而,也存在從低級語言到高級語言的編譯器,這類編譯器中用來從由高級語言生成的低級語言代碼重新生成高級語言代碼的又被叫做反編譯器。也有從一種高級語言生成另一種高級語言的編譯器,或者生成一種需要進一步處理的的中間代碼的編譯器(又叫級聯)。

典型的編譯器輸出是由包含入口點的名字和地址以及外部調用(到不在這個目標文件中的函數調用)的機器代碼所組成的目標文件。一組目標文件,不必是同一編譯器產生,但使用的編譯器必需採用同樣的輸出格式,可以鏈接在一起並生成可以由用戶直接執行的可執行程序。

編譯器種類

編譯器可以生成用來在與編譯器本身所在的計算機和操作系統(平台)相同的環境下運行的目標代碼,這種編譯器又叫做「本地」編譯器。另外,編譯器也可以生成用來在其它平台上運行的目標代碼,這種編譯器又叫做交叉編譯器。交叉編譯器在生成新的硬體平台時非常有用。「源碼到源碼編譯器」是指用一種高級語言作為輸入,輸出也是高級語言的編譯器。例如: 自動並行化編譯器經常採用一種高級語言作為輸入,轉換其中的代碼,並用並行代碼注釋對它進行注釋(如OpenMP)或者用語言構造進行注釋(如FORTRAN的DOALL指令)。

預處理器(preprocessor)

作用是通過代入預定義等程序段將源程序補充完整。

編譯器前端(frontend)

前端主要負責解析(parse)輸入的源程序,由詞法分析器和語法分析器協同工作。詞法分析器負責把源程序中的『單詞』(Token)找出來,語法分析器把這些分散的單詞按預先定義好的語法組裝成有意義的表達式,語句 ,函數等等。 例如「a = b + c;」前端詞法分析器看到的是「a, =, b , +, c;」,語法分析器按定義的語法,先把他們組裝成表達式「b + c」,再組裝成「a = b + c」的語句。 前端還負責語義(semantic checking)的檢查,例如檢測參與運算的變數是否是同一類型的,簡單的錯誤處理。最終的結果常常是一個抽象的語法樹(abstract syntax tree,或 AST),這樣後端可以在此基礎上進一步優化,處理。

編譯器後端(backend)

編譯器後端主要負責分析,優化中間代碼(Intermediate representation)以及生成機器代碼(Code Generation)。

一般說來所有的編譯器分析,優化,變型都可以分成兩大類: 函數內(intraproceral)還是函數之間(interproceral)進行。很明顯,函數間的分析,優化更准確,但需要更長的時間來完成。

編譯器分析(compiler analysis)的對象是前端生成並傳遞過來的中間代碼,現代的優化型編譯器(optimizing compiler)常常用好幾種層次的中間代碼來表示程序,高層的中間代碼(high level IR)接近輸入的源程序的格式,與輸入語言相關(language dependent),包含更多的全局性的信息,和源程序的結構;中層的中間代碼(middle level IR)與輸入語言無關,低層的中間代碼(Low level IR)與機器語言類似。 不同的分析,優化發生在最適合的那一層中間代碼上。

常見的編譯分析有函數調用樹(call tree),控制流程圖(Control flow graph),以及在此基礎上的變數定義-使用,使用-定義鏈(define-use/use-define or u-d/d-u chain),變數別名分析(alias analysis),指針分析(pointer analysis),數據依賴分析(data dependence analysis)等等。

上述的程序分析結果是編譯器優化(compiler optimization)和程序變形(compiler transformation)的前提條件。常見的優化和變新有:函數內嵌(inlining),無用代碼刪除(Dead code elimination),標准化循環結構(loop normalization),循環體展開(loop unrolling),循環體合並,分裂(loop fusion,loop fission),數組填充(array padding),等等。優化和變形的目的是減少代碼的長度,提高內存(memory),緩存(cache)的使用率,減少讀寫磁碟,訪問網路數據的頻率。更高級的優化甚至可以把序列化的代碼(serial code)變成並行運算,多線程的代碼(parallelized,multi-threaded code)。

機器代碼的生成是優化變型後的中間代碼轉換成機器指令的過程。現代編譯器主要採用生成匯編代碼(assembly code)的策略,而不直接生成二進制的目標代碼(binary object code)。即使在代碼生成階段,高級編譯器仍然要做很多分析,優化,變形的工作。例如如何分配寄存器(register allocatioin),如何選擇合適的機器指令(instruction selection),如何合並幾句代碼成一句等等。

❽ VC++6.0編譯器中怎麼設置編譯選項為多線程

/MT

「Project Settings」
選擇「C/C++」頁面標簽,然後在「Category」下拉式清單方塊中選擇「Code Generation」。在「Use Run-Time Library」下拉式清單方塊中,可以看到用於「Release」設定的「Single-Threaded」和用於Debug設定的「Debug Single-Threaded」。將這些分別改為「Multithreaded」和「Debug Multithreaded」。

❾ linux下c、c++下多線程編譯

C語言要求除main函數外 所有的函數必須先聲明才能使用 你可以在函數定義的時候一起聲明這個函數 但是在這個函數定義之前不能使用這個函數
下面用通俗點的語言講: 你在main函數中調用了thread函數, 但是如果你把void *thread(void *vargp);刪掉了, 那麼編譯器就找不到這個函數了(因為編譯器是從前往後編譯這個程序的) 因此編譯器是通不過的
有兩種方法, 一種就是像你之前寫的 先聲明這個函數 第二種是把void *thread(void *vargp){...}放到main函數的前面.
有些返回值和參數類型為int型的函數也可以不用聲明, 編譯器也能通過, 不過這是不建議的 也是不符合標準的
標准建議每個函數都應該給出它們的顯式的聲明
希望你懂了 嘿嘿

❿ C++多線程編程要用到哪些庫如何編譯這些庫

千萬別以為現在的C++沒有原生的多線程庫

OpenMP 是一個多線程庫,不過他還需要編譯器的支持,好在現在絕大多數都已經支持(這個可能是目前最流行的原生多線程庫了)

C++的標准頭process.h(太老的沒有,2002年後的基本都有)中有操作進程和執行環境的函數,能實現簡單的進程級或線程級並行操作。
使用起來非常非常方便。windows平台的C語言編譯工具也都有這個頭,unix平台上的unistd.h跟這個頭很相似,函數名與用法也基本一樣。

還有一些其他的第三方多線程庫,你可以網上搜搜,但是注意是否跨平台等問題

如果你要使用操作系統相關的多線程API,那麼也就沒什麼選擇餘地,windows上只能用windows的多線程API (參考MSDN) unix同理

OpenMP的優點是跨平台,功能豐富強大(例如提供了各種鎖、信號等),代碼改動也比較小,使用起來也非常方便快捷。缺點是沒有像直接用系統API時透明感,畢竟使用系統API時,程序員完全控制了邏輯,非常直觀,當然這也帶來了錯誤風險和代碼復雜度

閱讀全文

與編譯器後端多線程相關的資料

熱點內容
gcc編譯手冊pdf 瀏覽:584
梁箍筋未標注加密區 瀏覽:627
自家網路連不上上面顯示加密 瀏覽:386
編譯後無法運行圖片 瀏覽:592
linux系統修改文件命令 瀏覽:702
iphone如何安裝中國石化app 瀏覽:176
app怎麼寫簡歷 瀏覽:680
金蝶kis雲app怎麼樣 瀏覽:708
cad命令xr 瀏覽:296
f如何設置ftp伺服器 瀏覽:833
編程題兔子生兔子python 瀏覽:421
加密數字卡專利申請 瀏覽:783
我的世界命令方塊該怎麼拿 瀏覽:785
浙江容錯伺服器廠家雲空間 瀏覽:196
linuxpython3idle 瀏覽:741
程序員成就感從哪來 瀏覽:547
游資抄底源碼公式 瀏覽:804
用VF命令 瀏覽:950
解壓速度14m 瀏覽:333
php獲取httpheader 瀏覽:301