您的位置:首页 > 运维架构

getopt_long()解析命令行选项参数

2014-05-13 11:53 771 查看
#include

函数说明:

函数getopt用来解析命令行参数。

函数getopt_long支持长选项的命令行解析。

函数原型:

int getopt_long(int argc, char* const argv[],

const
char *optstring,

const
struct option *longopts,

int
*longindex);

参数:

argc、argv直接从main函数中获取。

opting是选项参数组成的字符串,由下列元素组成:

1.单个字符,表示选项,
2.单个字符后接一个冒号:表示该选项后必须跟一个参数。参数紧跟在选项后或者以空格隔开。该参数的指针赋给optarg。
3.单个字符后跟两个冒号,表示该选项后可以有参数也可以没有参数。如果有参数,参数必须紧跟在选项后不能以空格隔开。该参数的指针赋给optarg。(这个特性是GNU的扩张)。
optstring是一个字符串,表示可以接受的参数。例如,"a:b:cd",表示可以接受的参数是a,b,c,d,其中,a和b参数后面跟有更多的参数值。(例如:-a host -b name)

longopts是一个结构的实例

struct option

{

const char *name; //name表示的是长参数名

int has_arg; // has_arg有3个值,no_argument(或者是0),表示该参数后面不跟参数值

//
required_argument(或者是1),表示该参数后面一定要跟个参数值

//
optional_argument(或者是2),表示该参数后面可以跟,也可以不跟参数值

int *flag; //
用来决定getopt_long()的返回值是什么。

// flag是null,则函数会返回与该项option匹配的val值。

int val; // 和flag联合决定返回值

};

=========================================================================

给个例子:
struct option long_options[] = {
{"a123", required_argument, 0, 'a'},
{"c123", no_argument, 0, 'c'},
};
现在,如果命令行的参数是-a 123,那么调用getopt_long()将返回字符'a',并且将字符串123由optarg返回(注意注意!字符串123由optarg带回!optarg不需要定义,在getopt.h中已经有定义)。
那么,如果命令行参数是-c,那么调用getopt_long()将返回字符'c',而此时,optarg是null。
最后,当getopt_long()将命令行所有参数全部解析完成后,返回-1。
===========================================================================

以上来自网络,便于学习记忆摘录在这里,下面是自己的理解:

函数原型:int getopt_long(int argc, char* const argv[],

const
char *optstring,

const
struct option *longopts,

int
*longindex);

其中optstring为单个字符参数,称为short_opts。

而longopts为多个字符(即一个或多个单词连接)参数,称为long_opts。

参数longindex为longopts数组中的索引返回值。

具体用法参考suricata中main()函数中解析命令行参数:

// 短字符参数

char short_opts[] = "c:TDhi:l:q:d:r:us:S:U:VF:";

// 长字符参数

struct option long_opts[] = {
{"dump-config", 0, &dump_config, 1},
{"pfring", optional_argument, 0, 0},
{"pfring-int", required_argument, 0, 0},
{"pfring-cluster-id", required_argument, 0, 0},
{"pfring-cluster-type", required_argument, 0, 0},
{"af-packet", optional_argument, 0, 0},
{"pcap", optional_argument, 0, 0},
{"pcap-buffer-size", required_argument, 0, 0},
{"unittest-filter", required_argument, 0, 'U'},
{"list-app-layer-protos", 0, &list_app_layer_protocols, 1},
{"list-unittests", 0, &list_unittests, 1},
{"list-cuda-cards", 0, &list_cuda_cards, 1},
{"list-runmodes", 0, &list_runmodes, 1},
{"list-keywords", optional_argument, &list_keywords, 1},
{"runmode", required_argument, NULL, 0},
{"engine-analysis", 0, &engine_analysis, 1},
{"pidfile", required_argument, 0, 0},
{"init-errors-fatal", 0, 0, 0},
{"fatal-unittests", 0, 0, 0},
{"user", required_argument, 0, 0},
{"group", required_argument, 0, 0},
{"erf-in", required_argument, 0, 0},
{"dag", required_argument, 0, 0},
{"napatech", 0, 0, 0},
{"build-info", 0, &build_info, 1},
{NULL, 0, NULL, 0}
};
// 长字符数组索引
int option_index = 0;

// 以下是用法
while ((opt = getopt_long(argc, argv, short_opts, long_opts, &option_index)) != -1)
{
switch (opt)
{ // case为函数返回值
case 0:

if (strcmp((long_opts[option_index]).name , "pfring") == 0 || strcmp((long_opts[option_index]).name
, "pfring-int") == 0)

{

// TO-DO...

}

else if (strcmp((long_opts[option_index]).name , "pcap") == 0)

{

// TO-DO...

}

break;

case 'c':

break;

case 'T':

break;

default:

usage(argv[0]);

exit(EXIT_FAILURE);

}

}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: