Unix C语言编程示例
2015-05-31 00:00
393 查看
Unix C语言编程示例
时间:2015-02-28 21:37
作者:
lsgxeva
分类:
基础深入>>language>>C
摘要:
在unix的系统上编写一个简单的C语言测试演示
标签:
Freebsd Linux Unix C语言 测试演示
提示:
文章均来自网络,版权为原作者所有,如有侵犯权益,请联络我们.
1. gcc/g++ 命令的常用选项格式(选项 解释)
-o FILE 指定输出文件名,在编译为目标代码时,这一选项不是必须的。如果FILE没有指定,缺省文件名是a.out.
-c 只编译生成目标文件,不链接
-m486 针对 486 进行代码优化。
-O0 不进行优化处理。
-O 或 -O1 优化生成代码。
-O2 进一步优化。
-O3 比 -O2 更进一步优化,包括 inline 函数。
-w 关闭所有警告,建议不要使用此项
-Wall 允许发出gcc能提供的所有有用的警告,也可以用-W(warning)来标记指定的警告
-werror 把所有警告转换为错误,以在警告发生时中止编译过程
-MM 输出一个make兼容的相关列表
-v 显示在编译过程的每一步中用到的命令
-E 只运行 C 预编译器。
-shared 生成共享目标文件。通常用在建立共享库时。
-static 链接静态库,即执行静态链接
-lFOO 链接名为libFOO的函数库
-g 在可执行程序中包含标准调试信息
-ggdb 在可执行程序中包含只有GNU debugger才能使别的达两条是信息
-O 优化编译过的代码
-ON 指定代码优化的级别为N,o<=N<=3
-ansi 支持ANSI/ISO C的标准语法,取消GNU的语法扩展中与该标准有冲突的部分(但这一选项并不能保证生成ANSI兼容的代码) 这一选项将禁止 GNU C 的某些特色, 例如 asm 或 typeof 关键词。
-pedantic 允许发出ANSI/ISO C标准所列出的所有警告
-errors 允许发出ANSI/ISO C标准所列出的所有错误
-traditional 支持Kernighan & Ritchie C语法(如用旧式语法定义函数);如果不知道这个选项的含义,也没有关系
-IDIRECTORY 指定额外的头文件搜索路径DIRECTORY。
-LDIRECTORY 指定额外的函数库搜索路径DIRECTORY。
-DFOO=BAR 在命令行定义预处理宏FOO,其值为BAR
-IDIRNAME 将DIRNAME加入到头文件的搜索目录列表中
-LDIRNAME 将DIRNAME加入到库文件的搜索目录列表中,缺省情况下gcc 只链接共享库
-DMACRO 以字符串“1”定义 MACRO 宏。
-DMACRO=DEFN 以字符串“DEFN”定义 MACRO 宏。
-UMACRO 取消对 MACRO 宏的定义。
g++参数介绍
[介绍]
gcc and g++分别是gnu的c & c++编译器
gcc/g++在执行编译工作的时候,总共需要4步
1.预处理,生成.i的文件
预处理器cpp
2.将预处理后的文件不转换成汇编语言,生成文件.s
编译器egcs
3.有汇编变为目标代码(机器代码)生成.o的文件
汇编器as
4.连接目标代码,生成可执行程序
连接器ld
1.总体选项
-E
只激活预处理,这个不生成文件,你需要把它重定向到一个输出文件里
面.
例子用法:
gcc -E hello.c > pianoapan.txt
gcc -E hello.c | more
慢慢看吧,一个hello word 也要与处理成800行的代码
-S
只激活预处理和编译,就是指把文件编译成为汇编代码。
例子用法
gcc -S hello.c
他将生成.s的汇编代码,你可以用文本编辑器察看
-c
只激活预处理,编译,和汇编,也就是他只把程序做成obj文件
例子用法:
gcc -c hello.c
他将生成.o的obj文件
2.目录选项
-Idir
在你是用#include"file"的时候,gcc/g++会先在当前目录查找你所制定的头
文件,如果没有找到,他回到缺省的头文件目录找,如果使用-I制定了目录,他
回先在你所制定的目录查找,然后再按常规的顺序去找.
对于#include,gcc/g++会到-I制定的目录查找,查找不到,然后将到系
统的缺省的头文件目录查找
-include file
-i
相当于“#include”
包含某个代码,简单来说,就是便以某个文件,需要另一个文件的时候,就可以
用它设定,功能就相当于在代码中使用#include
例子用法:
gcc hello.c -include /root/pianopan.h
-I-
就是取消前一个参数的功能,所以一般在-Idir之后使用
-idirafter dir
在-I的目录里面查找失败,讲到这个目录里面查找.
-iprefix prefix
-iwithprefix dir
一般一起使用,当-I的目录查找失败,会到prefix+dir下查找
-Ldir
制定编译的时候,搜索库的路径。比如你自己的库,可以用它制定目录,不然
编译器将只在标准库的目录找。这个dir就是目录的名称。
-llibrary
制定编译的时候使用的库
例子用法
gcc -lcurses hello.c
使用ncurses库编译程序
3.调试选项
-g
只是编译器,在编译的时候,产生调试信息。
-gstabs
此选项以stabs格式声称调试信息,但是不包括gdb调试信息.
-gstabs+
此选项以stabs格式声称调试信息,并且包含仅供gdb使用的额外调试信息.
-ggdb
此选项将尽可能的生成gdb的可以使用的调试信息.
-glevel
请求生成调试信息,同时用level指出需要多少信息,默认的level值是2
4.链接方式选项:
-static 此选项将禁止使用动态库。
优点:程序运行不依赖于其他库
缺点:文件比较大
-shared (-G) 此选项将尽量使用动态库,为默认选项
优点:生成文件比较小
缺点:运行时需要系统提供动态库
-symbolic 建立共享目标文件的时候,把引用绑定到全局符号上.
对所有无法解析的引用作出警告(除非用连接编辑选项 `-Xlinker -z -Xlinker defs'取代)。
注:只有部分系统支持该选项.
5.错误与告警选项
-Wall 一般使用该选项,允许发出GCC能够提供的所有有用的警告。也可以用-W{warning}来标记指定的警告。
-pedantic 允许发出ANSI/ISO C标准所列出的所有警告
-pedantic-errors 允许发出ANSI/ISO C标准所列出的错误
-werror 把所有警告转换为错误,以在警告发生时中止编译过程
-w 关闭所有警告,建议不要使用此项
6.预处理选项
-Dmacro
相当于C语言中的#define macro
-Dmacro=defn
相当于C语言中的#define macro=defn
-Umacro
相当于C语言中的#undef macro
-undef
取消对任何非标准宏的定义
7.其他选项
-o
制定目标名称,缺省的时候,gcc 编译出来的文件是a.out,很难听,如果你和我有同感,改掉它,哈哈
例子用法
gcc -o hello.exe hello.c (哦,windows用习惯了)
gcc -o hello.asm -S hello.c
-O0
-O1
-O2
-O3
编译器的优化选项的4个级别,-O0表示没有优化,-O1为缺省值,-O3优化级别最高
-fpic 编译器就生成位置无关目标码.适用于共享库(shared library).
-fPIC 编译器就输出位置无关目标码.适用于动态连接(dynamic linking),即使分支需要大范围转移.
-v 显示详细的编译、汇编、连接命令
-pipe
使用管道代替编译中临时文件,在使用非gnu汇编工具的时候,可能有些问题
gcc -pipe -o hello.exe hello.c
-ansi
关闭gnu c中与ansi c不兼容的特性,激活ansi c的专有特性(包括禁止一些asm inline typeof关键字,以及UNIX,vax等预处理宏,
-fno-asm
此选项实现ansi选项的功能的一部分,它禁止将asm,inline和typeof用作关键字。
-fno-strict-prototype
只对g++起作用,使用这个选项,g++将对不带参数的函数,都认为是没有显式的对参数的个数和类型说明,而不是没有参数.而gcc无论是否使用这个参数,都将对没有带参数的函数,认为城没有显式说明的类型
-fthis-is-varialble
就是向传统c++看齐,可以使用this当一般变量使用.
-fcond-mismatch
允许条件表达式的第二和第三参数类型不匹配,表达式的值将为void类型
-funsigned-char
-fno-signed-char
-fsigned-char
-fno-unsigned-char
这四个参数是对char类型进行设置,决定将char类型设置成unsigned char(前
两个参数)或者 signed char(后两个参数)
-imacros file
将file文件的宏,扩展到gcc/g++的输入文件,宏定义本身并不出现在输入文件中
-nostdinc
使编译器不再系统缺省的头文件目录里面找头文件,一般和-I联合使用,明确限定头文件的位置
-nostdin C++
规定不在g++指定的标准路经中搜索,但仍在其他路径中搜索,.此选项在创建libg++库使用
-C
在预处理的时候,不删除注释信息,一般和-E使用,有时候分析程序,用这个很方便的
-M
生成文件关联的信息。包含目标文件所依赖的所有源代码你可以用gcc -M hello.c来测试一下,很简单。
-MM
和上面的那个一样,但是它将忽略由#include造成的依赖关系。
-MD
和-M相同,但是输出将导入到.d的文件里面
-MMD
和-MM相同,但是输出将导入到.d的文件里面
-Wa,option
此选项传递option给汇编程序;如果option中间有逗号,就将option分成多个选项,然后传递给会汇编程序
-Wl.option
此选项传递option给连接程序;如果option中间有逗号,就将option分成多个选项,然后传递给会连接程序.
-x language filename
设定文件所使用的语言,使后缀名无效,对以后的多个有效.也就是根
据约定C语言的后缀名称是.c的,而C++的后缀名是.C或者.cpp,如果
你很个性,决定你的C代码文件的后缀名是.pig 哈哈,那你就要用这
个参数,这个参数对他后面的文件名都起作用,除非到了下一个参数
的使用。
可以使用的参数吗有下面的这些
`c’, `objective-c’, `c-header’, `c++’, `cpp-output’,
`assembler’, and `assembler-with-cpp’.
看到英文,应该可以理解的。
例子用法:
gcc -x c hello.pig
-x none filename
关掉上一个选项,也就是让gcc根据文件名后缀,自动识别文件类型
例子用法:
gcc -x c hello.pig -x none hello2.c
debug_pos.h
*******************************************************************************************
/**
|----------------------------------------------
| Source File Header Section
|----------------------------------------------
| Copyright (C), 2008-2016, LSGX.
|
lsgxeva team. All rights reserved.
|
| @FileName
debug_pos.c
| @ModuleName
debug_pos
| @Author/Corporation
jjx/LSGX
lsgxthink@163.com
| @Version
V1.0
| @Date
2016-02-13 22:55:26
| @CPU
x86
| @RTOS
Linux, FreeBSD
| @Compiler
GCC V4.8.4
| @Description
Debugging error message positioning
| @License
MIT
| @Link http://git.oschina.net/lsgx
| @FileSource
none
| @Others
none
|
| @RevisionHistory
|----------------------------------------------
| @@Number
1001
| @@Version
V1.0
| @@Date
2016-02-13 22:55:26
| @@Author
jjx <lsgxthink AT 163 DOT com>
| @@ModuleName
debug_pos
| @@RevisionType
feat
| @@Scope
debug_pos
| @@Subject
Debugging error message positioning
|
| @@Description
| **************
| Debugging error message positioning
| and output information to the log file
|
|----------------------------------------------
*/
/**
|----------------------------------------------
| Multi-Include-Prevent Section
|----------------------------------------------
*/
#ifndef __DEBUG_POS_H__
#define __DEBUG_POS_H__
/**
|----------------------------------------------
| Debug switch Section
|----------------------------------------------
*/
//#define _DEBUG_POS_HIDE_
// 屏蔽DEBUG_POS功能的宏开关
/**
|----------------------------------------------
| Include File Section
|----------------------------------------------
*/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <fcntl.h>
#include <ctype.h>
#include <sys/types.h>
#include <limits.h>
#include <time.h>
#include <stdarg.h>
#include <errno.h>
#include <signal.h>
#include <sys/wait.h>
#include <sys/utsname.h>
#ifdef __unix__
#include <stdbool.h>
#define DllExport extern
#else
#include <windows.h>
#define DllExport __declspec( dllexport )
#endif // __unix__
/**
|----------------------------------------------
| Macro Define Section
|----------------------------------------------
*/
#ifdef __cplusplus
extern "C" {
#endif // __cplusplus
// 整数累加并防止溢出
#define DBGP_INC_SAT( val )
( val = ( (val) + 1 > (val) ) ? (val) + 1 : (val) )
// 返回数组元素的个数
#define DBGP_ARR_SIZE( arr )
( sizeof((arr)) / sizeof((arr[0])) )
// 判断指针是否为空并返回字符串
#define DBGP_IS_NULL( ptr )
(!(ptr) ? "null" : "non-null")
/**
|----------------------------------------------
| Structure Declare Section
|----------------------------------------------
*/
/**
|----------------------------------------------
| @Structure
enum ENUM_DEBUG_LEVEL
| @Description
调试打印信息的级别
| @Member
|
1: DEBUG_EMERG = 0
// 紧急事件对应的调试信息等级
|
2: DEBUG_ALERT = 1
// 报警事件对应的调试信息等级
|
3: DEBUG_CRIT = 2
// 临界事件对应的调试信息等级
|
4: DEBUG_ERR = 3
// 错误事件对应的调试信息等级
| 5: DEBUG_WARNING = 4
// 告警事件对应的调试信息等级
| 6: DEBUG_NOTICE = 5
// 提示事件对应的调试信息等级
| 7: DEBUG_INFO = 6
// 消息事件对应的调试信息等级
| 8: DEBUG_DEBUG = 7
// 调试事件对应的调试信息等级
| @Others
none
|----------------------------------------------
*/
enum ENUM_DEBUG_LEVEL {
DEBUG_EMERG = 0,
DEBUG_ALERT,
DEBUG_CRIT,
DEBUG_ERR,
DEBUG_WARNING,
DEBUG_NOTICE,
DEBUG_INFO,
DEBUG_DEBUG
};
#define DBGP_MAX_TITLE_LEN 20 // 调试标识字符串的最大长度
#define DBGP_MIN_TIME_LEN 20 // 存储时间字符串的最小长度
#define DBGP_MIN_PATH_LEN 512 // 存储进程名称符串的最小长度
#define DBGP_LOG_FILE_NAME "debug_pos.log" // 缺省的日志记录的文件
#define DBGP_LOG_FILE_MODE "at+" // 缺省的日志文件打开模式
#define DBGP_SER_MODE_NAME "DEBUG" // 调试的程序名称
#define DBGP_LIMIT_KILL_LEVEL DEBUG_ERR // 结束进程的最大调试等级的等级
/**
|----------------------------------------------
| @Structure
struct DEBUG_STR
| @Description
调试级别和调试标识
| @Member
|
1: level // 调试级别
|
2: title // 调试标识
| @Others
none
|----------------------------------------------
*/
struct DEBUG_STR {
const enum ENUM_DEBUG_LEVEL level;
const char title[DBGP_MAX_TITLE_LEN];
};
DllExport struct DEBUG_STR DEBUG_STR_ITEM[DEBUG_DEBUG+1];
// 返回调试等级对应的标识
#define DBGP_LEVEL_TITLE( debug_level ) (( debug_level >= 0 && debug_level <= ( DBGP_ARR_SIZE(DEBUG_STR_ITEM) - 1 ) ) ? DEBUG_STR_ITEM[debug_level].title : "level title unknow")
/**
|----------------------------------------------
| Global Variable Declare Section
|----------------------------------------------
*/
// 调试消息数量计数
DllExport unsigned long long int debug_count;
/**
|----------------------------------------------
| File Static Variable Declare Section
|----------------------------------------------
*/
/**
|----------------------------------------------
| Prototype Declare Section
|----------------------------------------------
*/
/**
|----------------------------------------------
| @Function
system_digital_time
| @Description
获取当前时间
| @Calls
|
1: localtime
// 把从1970-1-1零点零分到当前时间系统所偏移的秒数时间转换为本地时间
| @CalledBy
|
1: DEBUG_POS // 按级别打印调试信息的宏
| @TableAccessed
none
| @TableUpdated
none
| @FileAccessed
none
| @FileUpdated
none
| @Input
|
1: str_len
// 字符串空间的长度
| @Output
|
1: time_str
// 存储时间的字符串指针
| @Return
|
1: 0
// 正确或成功
|
2: -1
// 失败或错误
| @Example
none
| @Others
none
|----------------------------------------------
*/
DllExport int system_digital_time(char * time_str, const size_t str_len);
/**
|----------------------------------------------
| @Function
get_process_name
| @Description
获取当前进程pid的名称
| @Calls
|
1: getpid
// 获取当前进程的PID
| @CalledBy
|
1: DEBUG_POS // 按级别打印调试信息的宏
| @TableAccessed
none
| @TableUpdated
none
| @FileAccessed
none
| @FileUpdated
none
| @Input
|
1: name_len
// 字符串空间的长度
| @Output
|
1: process_name
// 存储进程名称的字符串指针
| @Return
|
1: 0
// 正确或成功
|
2: -1
// 失败或错误
| @Example
none
| @Others
none
|----------------------------------------------
*/
DllExport int get_process_name(char *process_name, const size_t name_len);
/**
|----------------------------------------------
| @Macro
DEBUG_POS
| @Description
按级别打印调试信息的宏
| @Calls
|
1: system_digital_time
// 获取当前进程的PID
|
2: get_process_name
// 获取当前进程pid的名称
|
3: abort
// 结束当前进程
| @CalledBy
none
| @TableAccessed
none
| @TableUpdated
none
| @FileAccessed
none
| @FileUpdated
DBGP_LOG_FILE_NAME
// 缺省的日志记录的文件
| @Input
|
1: debug_level
// 调试等级,枚举值(0-7)
|
2: ...
// 可变参数,格式化字符串
| @Output
none
| @Return
none
| @Example
none
| @Others
none
|----------------------------------------------
*/
#ifndef _DEBUG_POS_HIDE_
// 屏蔽DEBUG_POS功能的宏开关
#define DEBUG_POS(debug_level, ...) do { \
if ( debug_level >= 0 ) { \
bool debug_exit_stat = false; \
FILE * debug_pos_fp = NULL; \
debug_pos_fp = fopen(DBGP_LOG_FILE_NAME, DBGP_LOG_FILE_MODE); \
char time_str[DBGP_MAX_TITLE_LEN] = {'\0'}; \
system_digital_time(time_str, sizeof(time_str)); \
char process_name[DBGP_MIN_PATH_LEN] = {'\0'}; \
get_process_name(process_name, sizeof(process_name)); \
fprintf(debug_pos_fp, "[%s] <*** [%s] ***>\n\t[title: %s, time: %s, count: %llu]\n\t[file_name: %s, function_name: %s, line_no: %d]\n\t>>>> ", \
DBGP_SER_MODE_NAME, process_name, \
DBGP_LEVEL_TITLE(debug_level), \
time_str, DBGP_INC_SAT(debug_count), \
__FILE__, __FUNCTION__, __LINE__); \
fprintf(debug_pos_fp, __VA_ARGS__); \
fputc('\n', debug_pos_fp); \
if (debug_level <= DBGP_LIMIT_KILL_LEVEL) { \
fprintf(debug_pos_fp, "%s", "\t>>>> ****** [debug exit abort process] ******\n"); \
debug_exit_stat = true; \
} \
fclose(debug_pos_fp); \
if (debug_exit_stat) { \
abort(); \
} \
} \
} while(0)
#else
#define DEBUG_POS(debug_level, ...) NULL
#endif // _DEBUG_POS_HIDE_
/**
|----------------------------------------------
| @Macro
DEBUG_ASSERT
| @Description
断言打印调试信息的宏
| @Calls
|
1: DEBUG_POS
// 按级别打印调试信息的宏
| @CalledBy
none
| @TableAccessed
none
| @TableUpdated
none
| @FileAccessed
none
| @FileUpdated
DBGP_LOG_FILE_NAME
// 缺省的日志记录的文件
| @Input
|
1: condition
// 断言条件的真假
|
2: ...
// 可变参数,格式化字符串
| @Output
none
| @Return
none
| @Example
none
| @Others
none
|----------------------------------------------
*/
#define DEBUG_ASSERT(condition, ...) do { \
if (condition) { \
NULL; \
} else { \
DEBUG_POS(DBGP_LIMIT_KILL_LEVEL, __VA_ARGS__); \
} \
} while(0)
#ifdef __cplusplus
} /* extern "C" */
#endif // __cplusplus
#endif // __DEBUG_POS_H__
/* End of debug_pos.h */
*******************************************************************************************
debug_pos.c
*******************************************************************************************
/**
|----------------------------------------------
| Source File Header Section
|----------------------------------------------
| Copyright (C), 2008-2016, LSGX.
|
lsgxeva team. All rights reserved.
|
| @FileName
debug_pos.c
| @ModuleName
debug_pos
| @Author/Corporation
jjx/LSGX
lsgxthink@163.com
| @Version
V1.0
| @Date
2016-02-13 22:55:26
| @CPU
x86
| @RTOS
Linux, FreeBSD
| @Compiler
GCC V4.8.4
| @Description
Debugging error message positioning
| @License
MIT
| @Link http://git.oschina.net/lsgx
| @FileSource
none
| @Others
none
|
| @RevisionHistory
|----------------------------------------------
| @@Number
1001
| @@Version
V1.0
| @@Date
2016-02-13 22:55:26
| @@Author
jjx <lsgxthink AT 163 DOT com>
| @@ModuleName
debug_pos
| @@RevisionType
feat
| @@Scope
debug_pos
| @@Subject
Debugging error message positioning
|
| @@Description
| **************
| Debugging error message positioning
| and output information to the log file
|
|----------------------------------------------
*/
/**
|----------------------------------------------
| Debug switch Section
|----------------------------------------------
*/
/**
|----------------------------------------------
| Include File Section
|----------------------------------------------
*/
#include "debug_pos.h"
/**
|----------------------------------------------
| Macro Define Section
|----------------------------------------------
*/
#ifdef __cplusplus
extern "C" {
#endif // __cplusplus
/**
|----------------------------------------------
| Structure Define Section
|----------------------------------------------
*/
/**
| @Structure
struct DEBUG_STR
| @Description
调试级别和调试标识
| @Member
|
1: level // 调试级别
|
2: title // 调试标识
| @Others
none
*/
struct DEBUG_STR DEBUG_STR_ITEM[DEBUG_DEBUG+1] = {
{DEBUG_EMERG, "DEBUG_EMERG"}, /* system is unusable */ /* 紧急事件消息,系崩溃之前提示,表示系统不可用 */
{DEBUG_ALERT, "DEBUG_ALERT"}, /* action must be taken immediately */ /* 报警消息,表示必须立即采取措施 */
{DEBUG_CRIT, "DEBUG_CRIT"}, /* critical conditions */ /* 临界条件,通常涉及严重的硬件或软件操作失败 */
{DEBUG_ERR, "DEBUG_ERR"}, /* error conditions */ /* 错误条件,驱动程序用KERN_ERR来报告硬件的错误 */
{DEBUG_WARNING, "DEBUG_WARNING"}, /* warning conditions */ /* 告警条件,对可能现问题的情况进行警告 */
{DEBUG_NOTICE, "DEBUG_NOTICE"}, /* normal but significant condition */ /* 正常又重要的条件,用于提醒 */
{DEBUG_INFO, "DEBUG_INFO"}, /* informational */ /* 提示信息,如驱动程序启动时,打印硬件信息 */
{DEBUG_DEBUG, "DEBUG_DEBUG"} /* debug-level messages */ /* 调试级别的消息 */
};
/**
|----------------------------------------------
| Extern Prototype Declare Section
|----------------------------------------------
*/
/**
|----------------------------------------------
| Extern Variable Declare Section
|----------------------------------------------
*/
/**
|----------------------------------------------
| Global Variable Define Section
|----------------------------------------------
*/
// 调试消息数量计数
unsigned long long int debug_count = 0;
/**
|----------------------------------------------
| File Static Variable Define Section
|----------------------------------------------
*/
/**
|----------------------------------------------
| Prototype Define Section
|----------------------------------------------
*/
/**
|----------------------------------------------
| @Function
system_digital_time
| @Description
获取当前时间
| @Calls
|
1: localtime
// 把从1970-1-1零点零分到当前时间系统所偏移的秒数时间转换为本地时间
| @CalledBy
|
1: DEBUG_POS // 按级别打印调试信息的宏
| @TableAccessed
none
| @TableUpdated
none
| @FileAccessed
none
| @FileUpdated
none
| @Input
|
1: str_len
// 字符串空间的长度
| @Output
|
1: time_str
// 存储时间的字符串指针
| @Return
|
1: 0
// 正确或成功
|
2: -1
// 失败或错误
| @Example
none
| @Others
none
|----------------------------------------------
*/
int system_digital_time(char * time_str, const size_t str_len)
{
int iret = -1;
if ( NULL == time_str || 0 == str_len ) {
perror("parameter error");
iret = -1;
goto OUT;
}
if (str_len < DBGP_MIN_TIME_LEN) {
perror("time_str buffer size to low");
iret = -1;
goto OUT;
}
time_t now = time((time_t *)NULL);
struct tm * time_now = localtime(&now);
memset((void *)time_str, '\0', str_len);
snprintf(time_str, str_len, "%4d-%02d-%02d %02d:%02d:%02d",
time_now->tm_year + 1900,
time_now->tm_mon + 1,
time_now->tm_mday,
time_now->tm_hour,
time_now->tm_min,
time_now->tm_sec);
iret = 0;
return iret;
OUT:
return iret;
}
/**
|----------------------------------------------
| @Function
get_process_name
| @Description
获取当前进程pid的名称
| @Calls
|
1: getpid
// 获取当前进程的PID
| @CalledBy
|
1: DEBUG_POS // 按级别打印调试信息的宏
| @TableAccessed
none
| @TableUpdated
none
| @FileAccessed
none
| @FileUpdated
none
| @Input
|
1: name_len
// 字符串空间的长度
| @Output
|
1: process_name
// 存储进程名称的字符串指针
| @Return
|
1: 0
// 正确或成功
|
2: -1
// 失败或错误
| @Example
none
| @Others
none
|----------------------------------------------
*/
int get_process_name(char *process_name, const size_t name_len)
{
int iret = -1;
if ( NULL == process_name || 0 == name_len ) {
perror("parameter error");
iret = -1;
goto OUT;
}
if (name_len < DBGP_MIN_PATH_LEN) {
perror("process_name buffer size to low");
iret = -1;
goto OUT;
}
#ifdef __FreeBSD__
const char *exe_file = "/file";
#else
const char *exe_file = "/exe";
#endif
char proc_path[256] = {'\0'};
char pid_str[64] = {'\0'};
char path[DBGP_MIN_PATH_LEN] = {'\0'};
const char *proc_dir = "/proc/";
pid_t pid = getpid();
sprintf(pid_str, "%d", pid);
strcpy(proc_path, proc_dir);
strcat(proc_path, pid_str);
strcat(proc_path, exe_file);
int ch = readlink(proc_path, path, DBGP_MIN_PATH_LEN);
if (ch != -1) {
path[ch] = '\0';
memset((void *)process_name, '\0', name_len);
strncpy(process_name, path, ch);
iret = 0;
} else {
iret = -1;
}
return iret;
OUT:
return iret;
}
#ifdef __cplusplus
} /* extern "C" */
#endif // __cplusplus
/* End of debug_pos.c */
*******************************************************************************************
demo.c
***********************************************************************************************
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
// #define _DEBUG_POS_HIDE_
#include "debug_pos.h"
int main(int argc, char *argv[], char *envp[])
{
DEBUG_POS(DEBUG_DEBUG, "调试级别的消息");
DEBUG_POS(DEBUG_INFO, "提示信息,如驱动程序启动时,打印硬件信息");
DEBUG_POS(DEBUG_NOTICE, "正常又重要的条件,用于提醒");
DEBUG_POS(DEBUG_WARNING, "警告条件,对可能现问题的情况进行警告");
// DEBUG_POS(DEBUG_ERR, "错误条件,驱动程序用KERN_ERR来报告硬件的错误");
// DEBUG_POS(DEBUG_CRIT, "临界条件,通常涉及严重的硬件或软件操作失败");
// DEBUG_POS(DEBUG_ALERT, "报告消息,表示必须立即采取措施");
// DEBUG_POS(DEBUG_EMERG, "紧急事件消息,系崩溃之前提示,表示系统不可用");
DEBUG_ASSERT(true, "断言成功消息");
// DEBUG_ASSERT(false, "断言失败消息");
DEBUG_POS(DEBUG_NOTICE, "You have inputed total [%d] argments", argc);
for (int i = 0; i < argc; i++) {
DEBUG_POS(DEBUG_NOTICE, "arg(%d):[%s]", i, argv[i]);
}
DEBUG_POS(DEBUG_NOTICE, "*** [The follow is envp] ***");
for (int i = 0; envp[i] != NULL; i++) {
DEBUG_POS(DEBUG_NOTICE, "envp(%d):[%s]", i, envp[i]);
}
return 0;
}
*******************************************************************************************
Makefile
********************************************************************************************
#############################################################################
#
# Generic Makefile for C/C++ Program
#
# License: GPL (General Public License)
# Author: whyglinux <whyglinux AT gmail DOT com>
# Date: 2006/03/04 (version 0.1)
# 2007/03/24 (version 0.2)
# 2007/04/09 (version 0.3)
# 2007/06/26 (version 0.4)
# 2008/04/05 (version 0.5)
#
# Description:
# ------------
# This is an easily customizable makefile template. The purpose is to
# provide an instant building environment for C/C++ programs.
#
# It searches all the C/C++ source files in the specified directories,
# makes dependencies, compiles and links to form an executable.
#
# Besides its default ability to build C/C++ programs which use only
# standard C/C++ libraries, you can customize the Makefile to build
# those using other libraries. Once done, without any changes you can
# then build programs using the same or less libraries, even if source
# files are renamed, added or removed. Therefore, it is particularly
# convenient to use it to build codes for experimental or study use.
#
# GNU make is expected to use the Makefile. Other versions of makes
# may or may not work.
#
# Usage:
# ------
# 1. Copy the Makefile to your program directory.
# 2. Customize in the "Customizable Section" only if necessary:
# * to use non-standard C/C++ libraries, set pre-processor or compiler
# options to <MY_CFLAGS> and linker ones to <MY_LIBS>
# (See Makefile.gtk+-2.0 for an example)
# * to search sources in more directories, set to <SRCDIRS>
# * to specify your favorite program name, set to <PROGRAM>
# 3. Type make to start building your program.
#
# Make Target:
# ------------
# The Makefile provides the following targets to make:
# $ make compile and link
# $ make NODEP=yes compile and link without generating dependencies
# $ make objs compile only (no linking)
# $ make tags create tags for Emacs editor
# $ make ctags create ctags for VI editor
# $ make clean clean objects and the executable file
# $ make distclean clean objects, the executable and dependencies
# $ make help get the usage of the makefile
#
#===========================================================================
## Customizable Section: adapt those variables to suit your program.
##==========================================================================
# The directories in which source files reside.
# If not specified, only the current directory will be serached.
SRCDIRS = .
# The executable file name.
# If not specified, current directory name or `a.out' will be used.
TARGET_EXEC = demo
# BSD make provides $MACHINE, but GNU make doesn't
MACHINE ?= $(shell uname -m 2>/dev/null)
PROGRAM = $(addsuffix _$(MACHINE), $(TARGET_EXEC))
# Additional system include directories options.
INC_DIR :=
INC_DIR += /usr/include /usr/local/include
INC_DIR += $(HOME)/include ${SRCDIRS}/include
ALL_INC_DIR = $(addprefix -I, $(INC_DIR))
# Additional system library directories
LIB_DIR :=
LIB_DIR += /lib /usr/lib /usr/local/lib
LIB_DIR += $(HOME)/lib ${SRCDIRS}/lib
ALL_LIB_DIR = $(addprefix -L, $(LIB_DIR))
# The pre-processor options used by the cpp (man cpp for more).
CPPFLAGS :=
#CPPFLAGS += -Werror -pedantic-errors
CPPFLAGS += -Wall -Wextra -pedantic -Wfloat-equal -funsigned-char
# The pre-processor and compiler options.
# Users can override those variables from the command line.
CFLAGS :=
CFLAGS += -Wshadow -Wstrict-prototypes -Wpointer-arith -Wcast-qual -Wcast-align -Wwrite-strings -Wmissing-prototypes -Wnested-externs -Winline -Wundef
#CFLAGS += -pipe -ffast-math -g -pg -ggdb -O2
#CFLAGS += -Wno-long-long
CFLAGS += -U__STRICT_ANSI__ -std=gnu99
#CFLAGS += -D_DEBUG_POS_HIDE_
CXXFLAGS :=
CXXFLAGS += -fno-strict-prototype -Wctor-dtor-privacy -Wnon-virtual-dtor -Woverloaded-virtual -Wreorder
# The options used in linking as well as in any direct use of ld.
LDFLAGS :=
LDFLAGS += -Wl,-rpath=/usr/local/lib/gcc48
LDFLAGS += -lm -lpthread -lncurses
LDFLAGS += -lssl -lcrypto
## Implicit Section: change the following only when necessary.
##==========================================================================
# The source file types (headers excluded).
# .c indicates C source files, and others C++ ones.
SRCEXTS = .c .C .cc .cpp .CPP .c++ .cxx .cp
# The header file types.
HDREXTS = .h .H .hh .hpp .HPP .h++ .hxx .hp
# The C program compiler.
CC = gcc
# The C++ program compiler.
CXX = g++
# Un-comment the following line to compile C programs as C++ ones.
#CC = $(CXX)
# The command used to delete file.
RM = rm -f
ETAGS = etags
ETAGSFLAGS =
CTAGS = ctags
CTAGSFLAGS =
## Stable Section: usually no need to be changed. But you can add more.
##==========================================================================
SHELL = /bin/bash
EMPTY =
SPACE = $(EMPTY) $(EMPTY)
ifeq ($(PROGRAM),)
CUR_PATH_NAMES = $(subst /,$(SPACE),$(subst $(SPACE),_,$(CURDIR)))
PROGRAM = $(word $(words $(CUR_PATH_NAMES)),$(CUR_PATH_NAMES))
ifeq ($(PROGRAM),)
PROGRAM = a.out
endif
endif
ifeq ($(SRCDIRS),)
SRCDIRS = .
endif
SOURCES = $(foreach d,$(SRCDIRS),$(wildcard $(addprefix $(d)/*,$(SRCEXTS))))
HEADERS = $(foreach d,$(SRCDIRS),$(wildcard $(addprefix $(d)/*,$(HDREXTS))))
SRC_CXX = $(filter-out %.c,$(SOURCES))
OBJS = $(addsuffix .o, $(basename $(SOURCES)))
DEPS = $(OBJS:.o=.d)
## Define some useful variables.
DEP_OPT = $(shell if `$(CC) --version | grep "GCC" >/dev/null`; then \
echo "-MM -MP"; else echo "-M"; fi )
DEPEND = $(CC) $(DEP_OPT) $(ALL_INC_DIR) $(CPPFLAGS) $(CFLAGS)
DEPEND.d = $(subst -g ,,$(DEPEND))
COMPILE.c = $(CC) $(ALL_INC_DIR) $(CPPFLAGS) $(CFLAGS) -c
COMPILE.cxx = $(CXX) $(ALL_INC_DIR) $(CPPFLAGS) $(CXXFLAGS) -c
LINK.c = $(CC) $(ALL_INC_DIR) $(CPPFLAGS) $(CFLAGS) $(ALL_LIB_DIR) $(LDFLAGS)
LINK.cxx = $(CXX) $(ALL_INC_DIR) $(CPPFLAGS) $(CXXFLAGS) $(ALL_LIB_DIR) $(LDFLAGS)
.PHONY: all objs tags ctags clean distclean help show
# Delete the default suffixes
.SUFFIXES:
all: $(PROGRAM)
# Rules for creating dependency files (.d).
#------------------------------------------
%.d:%.c
@echo -n $(dir $<) > $@
@$(DEPEND.d) $< >> $@
%.d:%.C
@echo -n $(dir $<) > $@
@$(DEPEND.d) $< >> $@
%.d:%.cc
@echo -n $(dir $<) > $@
@$(DEPEND.d) $< >> $@
%.d:%.cpp
@echo -n $(dir $<) > $@
@$(DEPEND.d) $< >> $@
%.d:%.CPP
@echo -n $(dir $<) > $@
@$(DEPEND.d) $< >> $@
%.d:%.c++
@echo -n $(dir $<) > $@
@$(DEPEND.d) $< >> $@
%.d:%.cp
@echo -n $(dir $<) > $@
@$(DEPEND.d) $< >> $@
%.d:%.cxx
@echo -n $(dir $<) > $@
@$(DEPEND.d) $< >> $@
# Rules for generating object files (.o).
#----------------------------------------
objs:$(OBJS)
%.o:%.c
$(COMPILE.c) $< -o $@
%.o:%.C
$(COMPILE.cxx) $< -o $@
%.o:%.cc
$(COMPILE.cxx) $< -o $@
%.o:%.cpp
$(COMPILE.cxx) $< -o $@
%.o:%.CPP
$(COMPILE.cxx) $< -o $@
%.o:%.c++
$(COMPILE.cxx) $< -o $@
%.o:%.cp
$(COMPILE.cxx) $< -o $@
%.o:%.cxx
$(COMPILE.cxx) $< -o $@
# Rules for generating the tags.
#-------------------------------------
tags: $(HEADERS) $(SOURCES)
$(ETAGS) $(ETAGSFLAGS) $(HEADERS) $(SOURCES)
ctags: $(HEADERS) $(SOURCES)
$(CTAGS) $(CTAGSFLAGS) $(HEADERS) $(SOURCES)
# Rules for generating the executable.
#-------------------------------------
$(PROGRAM):$(OBJS)
ifeq ($(SRC_CXX),) # C program
$(LINK.c) $(OBJS) $(MY_LIBS) -o $@
@echo Type ./$@ to execute the program.
else # C++ program
$(LINK.cxx) $(OBJS) $(MY_LIBS) -o $@
@echo Type ./$@ to execute the program.
endif
# MODIFY START
#ifndef NODEP
ifdef NODEP
# MODIFY END
ifneq ($(DEPS),)
sinclude $(DEPS)
endif
endif
clean:
$(RM) $(OBJS) $(PROGRAM) $(PROGRAM).exe $(PROGRAM).elf $(PROGRAM).gmon
distclean: clean
$(RM) $(DEPS) TAGS
# Show help.
help:
@echo 'Generic Makefile for C/C++ Programs (gcmakefile) version 0.5'
@echo 'Copyright (C) 2007, 2008 whyglinux <whyglinux@hotmail.com>'
@echo
@echo 'Usage: make [TARGET]'
@echo 'TARGETS:'
@echo ' all (=make) compile and link.'
@echo ' NODEP=yes make without generating dependencies.'
@echo ' objs compile only (no linking).'
@echo ' tags create tags for Emacs editor.'
@echo ' ctags create ctags for VI editor.'
@echo ' clean clean objects and the executable file.'
@echo ' distclean clean objects, the executable and dependencies.'
@echo ' show show variables (for debug use only).'
@echo ' help print this message.'
@echo
@echo 'Report bugs to <whyglinux AT gmail DOT com>.'
# Show variables (for debug use only.)
show:
@echo 'PROGRAM :' $(PROGRAM)
@echo 'SRCDIRS :' $(SRCDIRS)
@echo 'HEADERS :' $(HEADERS)
@echo 'SOURCES :' $(SOURCES)
@echo 'SRC_CXX :' $(SRC_CXX)
@echo 'OBJS :' $(OBJS)
@echo 'DEPS :' $(DEPS)
@echo 'DEPEND :' $(DEPEND)
@echo 'COMPILE.c :' $(COMPILE.c)
@echo 'COMPILE.cxx :' $(COMPILE.cxx)
@echo 'link.c :' $(LINK.c)
@echo 'link.cxx :' $(LINK.cxx)
## End of the Makefile ## Suggestions are welcome ## All rights reserved ##
#############################################################################
********************************************************************************************
来自为知笔记(Wiz)
相关文章推荐
- C/C++&nbsp;函数指针,强制转换示例
- 一个简单的C/C++多线程
- C/C++求完数,小提醒
- C++ 实现杨辉三角
- C/C++用Unicode保存字符并输出
- C/C++素数判断(附exe方便不懂编程…
- C++刷题——线段分割平面
- 渣校ACM历程——番外之蓝桥杯决赛
- 【末世旅行之C语言】C语言经典试题小集合
- Error Tips
- 在C++里写一个不能被继承的类
- 汉诺塔的C语言实现
- ubuntu下c语言hello world
- swust oj 1132--Coin-collecting by robot
- swust oj 1139--Coin-row problem
- C++虚函数及虚函数表解析
- 高效编程——C++测试代码运行时间方法
- hdoj1160最长上升子序列
- C++内存管理详解
- C语言高级语法概述笔记