在 Linux 上,如果我安装了一个新软件包,并且其中包含我以前从未使用过的命令,有没有办法找到 MAN 页面或 --help 选项中未记录的隐藏选项和参数。
我最近遇到了几个软件包,其中有隐藏的选项,如果我不是在解决问题时从互联网上发现的话,我根本不会知道这些选项。
答案1
并非所有东西都是开源的,即使在 Linux 上也是如此,所以假设由于某种原因您无法获得源代码,可能只是因为您不想费心搜索源代码并下载或在线查看,您可以通过查找命令二进制文件中的字符串来找到线索。
该strings
命令专门用于从二进制文件中提取可读字符串。
例如,您现在知道命令ls
正在接受-T <tabsize>
选项,因此假设它正在用来getopt
解析其参数,字符序列T:
应该在getopt
选项列表中。
事实确实如此:
$ strings /bin/ls | grep T:
abcdfghiklmnopqrstuvw:xABCDFGHI:LNQRST:UXZ1
所有字母都是选项,因此您可以验证是否所有字母均已记录。
您可能还会寻找长选项,但除非您已经知道隐藏选项名称是什么,否则它会更复杂,因为您需要查看所有字符串。
如果您已经知道其中一个长选项,您可以将搜索限制在靠近该选项的字符串上。
继续看这个ls
案例,你会发现这个选项周围都有这些字符串tabsize
:
$ strings /bin/ls | less
...
no-group
hide-control-chars
reverse
almost-all
ignore-backups
classify
file-type
dereference-command-line
hide
ignore
dereference
literal
quote-name
recursive
show-control-chars
tabsize
time-style
block-size
context
author
help
答案2
您只能从中找到隐藏的选项和参数源代码,但这不是问题,因为 GNU/Linux 是开源的。对于用 C 编写的程序,你首先从main()
函数开始查看int argc
for参数计数和char *argv[]
参数指针数组得到处理。
#include <stdio.h>
int main( int argc, char *argv[] ) {
if( argc == 2 ) {
printf("The argument is %s\n", argv[1]);
}
else {
printf("Exactly one argument expected.\n");
}
}
选项也会作为参数从命令行传递给程序。如果使用以下方式传递选项getopt()
API,您可能会看到使用-while
循环检查选项。这允许解析选项及其参数,而不管它们的顺序如何。switch
case
通常,
getopt
在循环中调用。当getopt
返回时-1
,表示没有其他选项,循环终止。while ((c = getopt (argc, argv, "abc:")) != -1) switch (c) { case 'a': aflag = 1; break; case 'b': bflag = 1; break; case 'c': cvalue = optarg; break; case '?': if (optopt == 'c') fprintf (stderr, "Option -%c requires an argument.\n", optopt); else if (isprint (optopt)) fprintf (stderr, "Unknown option `-%c'.\n", optopt); else fprintf (stderr, "Unknown option character `\\x%x'.\n", optopt); return 1; default: abort (); }
第二个循环用于处理剩余的非选项参数。
for (index = optind; index < argc; index++) printf ("Non-option argument %s\n", argv[index]);
我将通过查找这些循环来开始搜索,然后再搜索其他地方的argv
使用情况。
答案3
未记录的功能/选项/开关的问题在于,当然没有标准的地方可以找到它们。
源代码是寻找受支持内容的最终(或可能是第一个)地方,但您可能需要一些软件开发背景才能阅读代码并理解某个功能的含义/实现。
许多忽视更新文档的开发人员仍会在Changelog
他们维护的文档中提及新功能。变更日志虽然通常非常简洁,但仍然是用普通英语而不是代码编写的。
即使开发人员不经常维护,打包者仍会维护一个更新日志,其中包含安全更新概述以及任何新功能反向移植。
通常由软件包维护者安装 Changelog/usr/share/doc/<package-name/
并在软件包本身中包含它的一个版本,在 Debian 和 Ubuntu 上 rpm -q -changelog <package>
使用或查询您已安装的 RPM 软件包。apt-get changelog <package>
一个不太明显的例子
:--
据我所知,对于支持该选项的许多命令(如果不是大多数命令)来说,该选项并没有明确记录,并且它已经成为一种略显晦涩的语法。
它起源于getopt
功能并用于“界定选项的结束和参数的开始”当您的论点(可能)看起来像选项时,您会使用它。例如这里