As title, the hexdump command is
$ hexdump -C -v files.bin
Write a simple tool is helpfull for the binary dump in the program...
1 #include
2 #include
3
4 #define BUF_SIZE 1024
5
6 int main(void)
7 {
8 int r;
9 unsigned char buf[BUF_SIZE];
10
11 int seed = 0;
12
13 while (1)
14 {
15 int i, j;
16
17 r = fread(buf, 1, BUF_SIZE, stdin);
18 if (0 == r)
19 {
20 break;
21 }
22
23 i = 0;
24
25 for (i = 0; i < r; i += 0x10, seed += 0x10)
26 {
27
28 printf("%08x ", seed);
29
30 j = i;
31 for (j = i; j < i + 0x10; j++)
32 {
33 if (0 == (j % 8))
34 {
35 printf(" ");
36 }
37 printf("%02x ", buf[j]);
38 }
39
40 j = i;
41 for (j = i; j < i + 0x10; j++)
42 {
43 if (0 == (j % 8))
44 {
45 printf(" ");
46 }
47 if ((buf[j] >= ' ') && (buf[j] <= '~'))
48 {
49 printf("%c", buf[j]);
50 }
51 else
52 {
53 printf(".");
54 }
55 }
56 printf("\n");
57 }
58 }
59
60 return 0;
61 }
62
The result is...
$ gcc -Wall ddc.c -o ddc
$
$ ./ddc < s.jpg
00000000 ff d8 ff e0 00 10 4a 46 49 46 00 01 01 00 00 01 ......JF IF......
00000010 00 01 00 00 ff db 00 43 00 08 06 06 07 06 05 08 .......C ........
00000020 07 07 07 09 09 08 0a 0c 14 0d 0c 0b 0b 0c 19 12 ........ ........
00000030 13 0f 14 1d 1a 1f 1e 1d 1a 1c 1c 20 24 2e 27 20 ........ ... $.'
00000040 22 2c 23 1c 1c 28 37 29 2c 30 31 34 34 34 1f 27 ",#..(7) ,01444.'
00000050 39 3d 38 32 3c 2e 33 34 32 ff c0 00 0b 08 00 08 9=82<.34 2.......
00000060 00 08 01 01 11 00 ff c4 00 1f 00 00 01 05 01 01 ........ ........
00000070 01 01 01 01 00 00 00 00 00 00 00 00 01 02 03 04 ........ ........
00000080 05 06 07 08 09 0a 0b ff c4 00 b5 10 00 02 01 03 ........ ........
00000090 03 02 04 03 05 05 04 04 00 00 01 7d 01 02 03 00 ........ ...}....
000000a0 04 11 05 12 21 31 41 06 13 51 61 07 22 71 14 32 ....!1A. .Qa."q.2
000000b0 81 91 a1 08 23 42 b1 c1 15 52 d1 f0 24 33 62 72 ....#B.. .R..$3br
000000c0 82 09 0a 16 17 18 19 1a 25 26 27 28 29 2a 34 35 ........ %&'()*45
000000d0 36 37 38 39 3a 43 44 45 46 47 48 49 4a 53 54 55 6789:CDE FGHIJSTU
000000e0 56 57 58 59 5a 63 64 65 66 67 68 69 6a 73 74 75 VWXYZcde fghijstu
000000f0 76 77 78 79 7a 83 84 85 86 87 88 89 8a 92 93 94 vwxyz... ........
00000100 95 96 97 98 99 9a a2 a3 a4 a5 a6 a7 a8 a9 aa b2 ........ ........
00000110 b3 b4 b5 b6 b7 b8 b9 ba c2 c3 c4 c5 c6 c7 c8 c9 ........ ........
00000120 ca d2 d3 d4 d5 d6 d7 d8 d9 da e1 e2 e3 e4 e5 e6 ........ ........
00000130 e7 e8 e9 ea f1 f2 f3 f4 f5 f6 f7 f8 f9 fa ff da ........ ........
00000140 00 08 01 01 00 00 3f 00 f0 ba ff d9 18 07 24 00 ......?. ......$.
$
Showing posts with label C Language. Show all posts
Showing posts with label C Language. Show all posts
Tuesday, December 24, 2013
Saturday, December 21, 2013
Bit operation
於system driver中,時常遇到bit的操作...
比方說要將某bit設成1或0
或這要看看某些bit有無on/off
可以以以下方式操作
#define BIT0 0x00000001
#define BIT1 0x00000002
#define BIT2 0x00000004
#define BIT3 0x00000008
#define BIT4 0x00000010
#define BIT5 0x00000020
#define BIT6 0x00000040
#define BIT7 0x00000080
#define REG_BASE 0x80000000
typedef unsigned int u32;
#define REG_BIT_SET(reg, bit) \
(*(volatile u32 *)(REG_BASE + reg) |= (bit))
#define REG_BIT_GET(reg, bit) \
(*(volatile u32 *)(REG_BASE + reg) & (bit))
#define REG_BIT_CLR(reg, bit) \
(*(volatile u32 *)(REG_BASE + reg) &= ~(bit))
比方說要將某bit設成1或0
或這要看看某些bit有無on/off
可以以以下方式操作
#define BIT0 0x00000001
#define BIT1 0x00000002
#define BIT2 0x00000004
#define BIT3 0x00000008
#define BIT4 0x00000010
#define BIT5 0x00000020
#define BIT6 0x00000040
#define BIT7 0x00000080
#define REG_BASE 0x80000000
typedef unsigned int u32;
#define REG_BIT_SET(reg, bit) \
(*(volatile u32 *)(REG_BASE + reg) |= (bit))
#define REG_BIT_GET(reg, bit) \
(*(volatile u32 *)(REG_BASE + reg) & (bit))
#define REG_BIT_CLR(reg, bit) \
(*(volatile u32 *)(REG_BASE + reg) &= ~(bit))
Thursday, August 27, 2009
Hello World入門(4)
這是Hello World程式的註解。
Hello World的入門,宅爸爸就暫時學習到這邊。
最後,以Hello World跟Makefile結合,做到編譯HelldWorld.c使用兩階段(編譯、連結)
1 /*
2 引入header file,目的是讓
3 compiler找到printf的宣告
4 */
5 #include <stdio.h>
6
7 /*
8 定義main為不需要參數,傳回
9 值為整屬的函數。main函數為
10 C語言程式中默認的進入點
11 */
12 int main(void)
13 {
14
15 /*
16 使用printf函數,輸出
17 Hello World字串至標準輸出
18 */
19 printf("Hello World\n");
20
21 /*
22 使函數結束,並傳回值0
23 */
24 return 0;
25 }
Hello World的入門,宅爸爸就暫時學習到這邊。
最後,以Hello World跟Makefile結合,做到編譯HelldWorld.c使用兩階段(編譯、連結)
1 # Copyright (C) 2009 Lung.S.Wu
2
3 #ARCH=
4 #TARGET=$(ARCH)-elf-
5
6 HEADER=head.h
7 SRC=HelloWorld.c
8 OBJ=$(SRC:%.c=%.o)
9 EXE=HelloWorld
10
11 CC=$(TARGET)gcc
12 LD=$(TARGET)ld
13
14 CFLAGS=-O3 -g -Wall
15
16 #.SILENT:
17
18 all:$(EXE)
19
20 $(EXE): $(OBJ)
21 $(CC) $(CFLAGS) $^ -o $@
22
23 %.o: %.c $(HEADER)
24 $(CC) -c $(CFLAGS) $< -o $@
25
26 clean:
27 rm -rf $(OBJ) $(EXE)
goto怎麼用?
宅爸爸學到goto這東西...
教科書上寫到儘量不用它,以免增加程式的複雜度,
以下就是一個很標準因為goto使用不當的鬼打牆的程式...
但有些狀況宅爸爸沒用goto這東西會讓程式變的很容易出錯,這是一個很矛盾的狀況...
尤其是在事後修改、維護這些程式時,program 1我會很容易搞混,而program 2比較有效率。
如果program2沒有用goto,return的處理就很麻煩,情況如下...
program 2若要修改,要增加一個return點,只要goto到合適的地方就行。
program 3的處理情況,要重複的關閉已開啟的handle,再做return,科科...。
goto在C語言中式保留字,不是函數,是無條件的跳躍到指定的程式中,但只限於單一函式範圍內。
教科書上寫到儘量不用它,以免增加程式的複雜度,
以下就是一個很標準因為goto使用不當的鬼打牆的程式...
1 /******************************
2 * goto program 1
3 ******************************/
4 void function(void)
5 {
6 int i = 0;
7
8 label1:
9 printf("Hello World\n");
10 if (i != 0)
11 {
12 return;
13 }
14 goto label3;
15
16 label2:
17 printf("What is it?\n");
18 i = 1;
19 goto label1;
20
21 label3:
22 printf("Here is it\n");
23 goto label2;
24 }
25
但有些狀況宅爸爸沒用goto這東西會讓程式變的很容易出錯,這是一個很矛盾的狀況...
1 /******************************
2 * goto program 2
3 * This is a C pseudo code
4 ******************************/
5 int function(void)
6 {
7 int ret = -1;
8 Handle h1, h2, h3;
9
10 h1 = HandleOpen(...);
11 if (error == h1)
12 {
13 goto return_f;
14 }
15
16 h2 = HandleOpen(...);
17 if (error == h2)
18 {
19 goto close_h1;
20 }
21
22 /* Error happened ... */
23 if (error)
24 {
25 goto close_h2;
26 }
27
28 h3 = HandleOpen(...);
29 if (error == h3)
30 {
31 goto close_h2;
32 }
33
34 /* Error happened ... */
35 if (error)
36 {
37 goto close_h3;
38 }
39
40 /* Other code ... */
41
42 ret = 0;
43 close_h3:
44 HandleClose(h3);
45 close_h2:
46 HandleClose(h2);
47 close_h1:
48 HandleClose(h1);
49 return_f:
50 return ret;
51 }
52
尤其是在事後修改、維護這些程式時,program 1我會很容易搞混,而program 2比較有效率。
如果program2沒有用goto,return的處理就很麻煩,情況如下...
1 /******************************
2 * goto program 3
3 * This is a C pseudo code
4 ******************************/
5 int function(void)
6 {
7 int ret = -1;
8 Handle h1, h2, h3;
9
10 h1 = HandleOpen(...);
11 if (error == h1)
12 {
13 return ret;
14 }
15
16 h2 = HandleOpen(...);
17 if (error == h2)
18 {
19 HandleClose(h1);
20 return ret;
21 }
22
23 /* Error happened ... */
24 if (error)
25 {
26 HandleClose(h1);
27 return ret;
28 }
29
30 h3 = HandleOpen(...);
31 if (error == h3)
32 {
33 HandleClose(h1);
34 HandleClose(h2);
35 return ret;
36 }
37
38 /* Error happened ... */
39 if (error)
40 {
41 HandleClose(h1);
42 HandleClose(h2);
43 HandleClose(h3);
44 return ret;
45 }
46
47 /* Other code ... */
48
49 ret = 0;
50 return ret;
51 }
52
program 2若要修改,要增加一個return點,只要goto到合適的地方就行。
program 3的處理情況,要重複的關閉已開啟的handle,再做return,科科...。
goto在C語言中式保留字,不是函數,是無條件的跳躍到指定的程式中,但只限於單一函式範圍內。
Tuesday, August 25, 2009
Hello World入門(3)
於Hello World入門(2)中一個檔案HelloWorld.c,它是一隻C語言程式。
傳統上,C語言程式檔案都以.c或者.h檔為結尾,本程式也不例外。
要使此程式可以執行,需經過C compiler編譯、連結無誤之後產生一可執行檔。
這裡補充說明,C語言語法是一個標準,現在標準官方網站。
而有不同的廠商、團體根據C語言標準製作他們自產的編譯器,比方說Microsoft,GNU,Intel...。
現在以GNU製作的編譯器為例,要將HelloWorld.c編譯成執行檔,
我習慣以底下命令編譯C語言程式...
這將會產生HelloWorld的執行檔。
gcc:GNU C編譯器的命令
-Wall:gcc參數,列出所有gcc認為有危險、不妥當程式碼片段
HelloWorld.c:程式設計者所編寫程式檔名
-o HelloWorld:指定編譯完成的執行檔為名稱,若無此參數預設檔名為a.out
很多理論的書本中提到,將一的原始程式要編譯成執行檔的過程,需經過以下步驟...
1.編譯。2.連結。
或者...
1.編譯。2.組譯。3.連結。
GNU C編譯器也不例外,遵循以上三步驟的慣例,我們可以用以下方式編譯
$gcc -Wall -v HelloWorld.c -o HelloWorld
得到編譯時的詳細內容、步驟
Using built-in specs.
Target: i486-linux-gnu
Configured with: ../src/configure -v --with-pkgversion='Debian 4.3.2-1.1' --with-bugurl=file:///usr/share/doc/gcc-4.3/README.Bugs --enable-languages=c,c++,fortran,objc,obj-c++ --prefix=/usr --enable-shared --with-system-zlib --libexecdir=/usr/lib --without-included-gettext --enable-threads=posix --enable-nls --with-gxx-include-dir=/usr/include/c++/4.3 --program-suffix=-4.3 --enable-clocale=gnu --enable-libstdcxx-debug --enable-objc-gc --enable-mpfr --enable-targets=all --enable-cld --enable-checking=release --build=i486-linux-gnu --host=i486-linux-gnu --target=i486-linux-gnu
Thread model: posix
gcc version 4.3.2 (Debian 4.3.2-1.1)
COLLECT_GCC_OPTIONS='-Wall' '-v' '-o' 'HelloWorld' '-mtune=generic'
/usr/lib/gcc/i486-linux-gnu/4.3.2/cc1 -quiet -v HelloWorld.c -quiet -dumpbase HelloWorld.c -mtune=generic -auxbase HelloWorld -Wall -version -o /tmp/cc3KesF0.s
ignoring nonexistent directory "/usr/local/include/i486-linux-gnu"
ignoring nonexistent directory "/usr/lib/gcc/i486-linux-gnu/4.3.2/../../../../i486-linux-gnu/include"
#include "..." search starts here:
#include <...> search starts here:
/usr/local/include
/usr/lib/gcc/i486-linux-gnu/4.3.2/include
/usr/lib/gcc/i486-linux-gnu/4.3.2/include-fixed
/usr/include/i486-linux-gnu
/usr/include
End of search list.
GNU C (Debian 4.3.2-1.1) version 4.3.2 (i486-linux-gnu)
compiled by GNU C version 4.3.2, GMP version 4.2.2, MPFR version 2.3.2.
warning: MPFR header version 2.3.2 differs from library version 2.3.1.
GGC heuristics: --param ggc-min-expand=99 --param ggc-min-heapsize=129511
Compiler executable checksum: c4cd35f2318868df36b839e33a8e2089
COLLECT_GCC_OPTIONS='-Wall' '-v' '-o' 'HelloWorld' '-mtune=generic'
as -V -Qy -o /tmp/ccA8J2A1.o /tmp/cc3KesF0.s
GNU assembler version 2.18.0 (i486-linux-gnu) using BFD version (GNU Binutils for Debian) 2.18.0.20080103
COMPILER_PATH=/usr/lib/gcc/i486-linux-gnu/4.3.2/:/usr/lib/gcc/i486-linux-gnu/4.3.2/:/usr/lib/gcc/i486-linux-gnu/:/usr/lib/gcc/i486-linux-gnu/4.3.2/:/usr/lib/gcc/i486-linux-gnu/:/usr/lib/gcc/i486-linux-gnu/4.3.2/:/usr/lib/gcc/i486-linux-gnu/
LIBRARY_PATH=/usr/lib/gcc/i486-linux-gnu/4.3.2/:/usr/lib/gcc/i486-linux-gnu/4.3.2/:/usr/lib/gcc/i486-linux-gnu/4.3.2/../../../../lib/:/lib/../lib/:/usr/lib/../lib/:/usr/lib/gcc/i486-linux-gnu/4.3.2/../../../:/lib/:/usr/lib/
COLLECT_GCC_OPTIONS='-Wall' '-v' '-o' 'HelloWorld' '-mtune=generic'
/usr/lib/gcc/i486-linux-gnu/4.3.2/collect2 --eh-frame-hdr -m elf_i386 --hash-style=both -dynamic-linker /lib/ld-linux.so.2 -o HelloWorld /usr/lib/gcc/i486-linux-gnu/4.3.2/../../../../lib/crt1.o /usr/lib/gcc/i486-linux-gnu/4.3.2/../../../../lib/crti.o /usr/lib/gcc/i486-linux-gnu/4.3.2/crtbegin.o -L/usr/lib/gcc/i486-linux-gnu/4.3.2 -L/usr/lib/gcc/i486-linux-gnu/4.3.2 -L/usr/lib/gcc/i486-linux-gnu/4.3.2/../../../../lib -L/lib/../lib -L/usr/lib/../lib -L/usr/lib/gcc/i486-linux-gnu/4.3.2/../../.. /tmp/ccA8J2A1.o -lgcc --as-needed -lgcc_s --no-as-needed -lc -lgcc --as-needed -lgcc_s --no-as-needed /usr/lib/gcc/i486-linux-gnu/4.3.2/crtend.o /usr/lib/gcc/i486-linux-gnu/4.3.2/../../../../lib/crtn.o
以上囉哩八說這麼多,只要抓住底下的要點
/usr/lib/gcc/i486-linux-gnu/4.3.2/cc1
為第一步驟...編譯,產生一個組合語言程式。
as -V -Qy -o /tmp/ccA8J2A1.o /tmp/cc3KesF0.s
為第二步驟...將第一步驟產生的組合語言程式做組譯工作,
產生object code(中文我不會翻譯)。
/usr/lib/gcc/i486-linux-gnu/4.3.2/collect2
為第二步驟...將第二步驟產生的object code做聯結(link)工作,
產稱執行程式。
做最後補充,連結的步驟可以將一個以上的object聯結(link)成一個執行程式。
之所以會有聯結(link)的步驟,最主要目的是...
可以將很大一段的程式碼分割成很多的程式檔,個別編譯,方便程式管理。
將程式是分割,若發生編譯錯誤,只需修改、編譯錯誤的程式,不需所有程式重新編譯,以節省編譯時間。
可以將已編譯的object code交給第三者,達到資料隱藏。
連結他人撰寫編譯好的程式庫(動作和上一點相反)
使執行檔於執行時,做好程式碼於記憶體中的佈局規劃。
增加執行檔檔頭,使program loader辨認、讀取相關訊息。
一般狀況而言,也會自動聯結系統預設的程式庫。
傳統上,C語言程式檔案都以.c或者.h檔為結尾,本程式也不例外。
要使此程式可以執行,需經過C compiler編譯、連結無誤之後產生一可執行檔。
這裡補充說明,C語言語法是一個標準,現在標準官方網站。
而有不同的廠商、團體根據C語言標準製作他們自產的編譯器,比方說Microsoft,GNU,Intel...。
現在以GNU製作的編譯器為例,要將HelloWorld.c編譯成執行檔,
我習慣以底下命令編譯C語言程式...
gcc -Wall HelloWorld.c -o HelloWorld
這將會產生HelloWorld的執行檔。
很多理論的書本中提到,將一的原始程式要編譯成執行檔的過程,需經過以下步驟...
1.編譯。2.連結。
或者...
1.編譯。2.組譯。3.連結。
GNU C編譯器也不例外,遵循以上三步驟的慣例,我們可以用以下方式編譯
$gcc -Wall -v HelloWorld.c -o HelloWorld
得到編譯時的詳細內容、步驟
Using built-in specs.
Target: i486-linux-gnu
Configured with: ../src/configure -v --with-pkgversion='Debian 4.3.2-1.1' --with-bugurl=file:///usr/share/doc/gcc-4.3/README.Bugs --enable-languages=c,c++,fortran,objc,obj-c++ --prefix=/usr --enable-shared --with-system-zlib --libexecdir=/usr/lib --without-included-gettext --enable-threads=posix --enable-nls --with-gxx-include-dir=/usr/include/c++/4.3 --program-suffix=-4.3 --enable-clocale=gnu --enable-libstdcxx-debug --enable-objc-gc --enable-mpfr --enable-targets=all --enable-cld --enable-checking=release --build=i486-linux-gnu --host=i486-linux-gnu --target=i486-linux-gnu
Thread model: posix
gcc version 4.3.2 (Debian 4.3.2-1.1)
COLLECT_GCC_OPTIONS='-Wall' '-v' '-o' 'HelloWorld' '-mtune=generic'
/usr/lib/gcc/i486-linux-gnu/4.3.2/cc1 -quiet -v HelloWorld.c -quiet -dumpbase HelloWorld.c -mtune=generic -auxbase HelloWorld -Wall -version -o /tmp/cc3KesF0.s
ignoring nonexistent directory "/usr/local/include/i486-linux-gnu"
ignoring nonexistent directory "/usr/lib/gcc/i486-linux-gnu/4.3.2/../../../../i486-linux-gnu/include"
#include "..." search starts here:
#include <...> search starts here:
/usr/local/include
/usr/lib/gcc/i486-linux-gnu/4.3.2/include
/usr/lib/gcc/i486-linux-gnu/4.3.2/include-fixed
/usr/include/i486-linux-gnu
/usr/include
End of search list.
GNU C (Debian 4.3.2-1.1) version 4.3.2 (i486-linux-gnu)
compiled by GNU C version 4.3.2, GMP version 4.2.2, MPFR version 2.3.2.
warning: MPFR header version 2.3.2 differs from library version 2.3.1.
GGC heuristics: --param ggc-min-expand=99 --param ggc-min-heapsize=129511
Compiler executable checksum: c4cd35f2318868df36b839e33a8e2089
COLLECT_GCC_OPTIONS='-Wall' '-v' '-o' 'HelloWorld' '-mtune=generic'
as -V -Qy -o /tmp/ccA8J2A1.o /tmp/cc3KesF0.s
GNU assembler version 2.18.0 (i486-linux-gnu) using BFD version (GNU Binutils for Debian) 2.18.0.20080103
COMPILER_PATH=/usr/lib/gcc/i486-linux-gnu/4.3.2/:/usr/lib/gcc/i486-linux-gnu/4.3.2/:/usr/lib/gcc/i486-linux-gnu/:/usr/lib/gcc/i486-linux-gnu/4.3.2/:/usr/lib/gcc/i486-linux-gnu/:/usr/lib/gcc/i486-linux-gnu/4.3.2/:/usr/lib/gcc/i486-linux-gnu/
LIBRARY_PATH=/usr/lib/gcc/i486-linux-gnu/4.3.2/:/usr/lib/gcc/i486-linux-gnu/4.3.2/:/usr/lib/gcc/i486-linux-gnu/4.3.2/../../../../lib/:/lib/../lib/:/usr/lib/../lib/:/usr/lib/gcc/i486-linux-gnu/4.3.2/../../../:/lib/:/usr/lib/
COLLECT_GCC_OPTIONS='-Wall' '-v' '-o' 'HelloWorld' '-mtune=generic'
/usr/lib/gcc/i486-linux-gnu/4.3.2/collect2 --eh-frame-hdr -m elf_i386 --hash-style=both -dynamic-linker /lib/ld-linux.so.2 -o HelloWorld /usr/lib/gcc/i486-linux-gnu/4.3.2/../../../../lib/crt1.o /usr/lib/gcc/i486-linux-gnu/4.3.2/../../../../lib/crti.o /usr/lib/gcc/i486-linux-gnu/4.3.2/crtbegin.o -L/usr/lib/gcc/i486-linux-gnu/4.3.2 -L/usr/lib/gcc/i486-linux-gnu/4.3.2 -L/usr/lib/gcc/i486-linux-gnu/4.3.2/../../../../lib -L/lib/../lib -L/usr/lib/../lib -L/usr/lib/gcc/i486-linux-gnu/4.3.2/../../.. /tmp/ccA8J2A1.o -lgcc --as-needed -lgcc_s --no-as-needed -lc -lgcc --as-needed -lgcc_s --no-as-needed /usr/lib/gcc/i486-linux-gnu/4.3.2/crtend.o /usr/lib/gcc/i486-linux-gnu/4.3.2/../../../../lib/crtn.o
以上囉哩八說這麼多,只要抓住底下的要點
/usr/lib/gcc/i486-linux-gnu/4.3.2/cc1
為第一步驟...編譯,產生一個組合語言程式。
as -V -Qy -o /tmp/ccA8J2A1.o /tmp/cc3KesF0.s
為第二步驟...將第一步驟產生的組合語言程式做組譯工作,
產生object code(中文我不會翻譯)。
/usr/lib/gcc/i486-linux-gnu/4.3.2/collect2
為第二步驟...將第二步驟產生的object code做聯結(link)工作,
產稱執行程式。
做最後補充,連結的步驟可以將一個以上的object聯結(link)成一個執行程式。
之所以會有聯結(link)的步驟,最主要目的是...
Wednesday, August 19, 2009
C語言參考資料
C Language refernce book
Books:
The C programming Language
C, A refernce Manual
The C standard
Advanced Programming in the UNIX Environment
Internet Document
C Langauge FAQ
C Language FAQ(中文版)
Books:
The C programming Language
C, A refernce Manual
The C standard
Advanced Programming in the UNIX Environment
Internet Document
C Langauge FAQ
C Language FAQ(中文版)
Subscribe to:
Posts (Atom)