我是否正确地认为 strcmp 对于文字来说是等效的(并且安全的)?

发布于 2024-07-11 18:15:56 字数 363 浏览 8 评论 0原文

我们都知道溢出可能导致的麻烦,这就是 strn* 存在的原因 - 并且大多数时候它们是有意义的。 但是,我见过使用 strncmp 来比较命令行参数的代码,如下所示:

if(... strncmp(argv[i], "--help", 6) == 0

现在,我认为这是不必要的,甚至可能是危险的(对于较长的参数,很容易错误计算文字中的字符)。

strncmp 在 null 上停止,并且代码已经假设 argv[i] 以 null 终止。 任何字符串文字都保证以 null 结尾,那么为什么不使用 strcmp 呢?

也许我错过了一些东西,但我已经见过几次了,这次它引起了我的兴趣,所以我想问一下。

We all know the trouble overflows can cause, and this is why strn* exist - and most of the time they make sense. However, I have seen code which uses strncmp to compare commandline parameters like so:

if(... strncmp(argv[i], "--help", 6) == 0

Now, I would have thought that this is unnecessary and perhaps even dangerous (for longer parameters it would be easy to miscount the characters in the literal).

strncmp stops on nulls, and the code already assumes argv[i] is null-terminated. Any string literal is guaranteed to be null-terminated, so why not use strcmp?

Perhaps I'm missing something, but I've seen this a few times and this time it intrigued me enough to ask.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(9

不醒的梦 2024-07-18 18:15:56

是的,这是完全安全的,并且被认为是标准做法。 字符串文字保证以正确的 null 结尾。

yes it is perfectly safe and considered standard practice. String literals are guaranteed to be properly null terminated.

烟─花易冷 2024-07-18 18:15:56

您确定该代码不是为了匹配
“--helpmedosoemthingwithareallylongoptionname”

Are you sure that the code is not intended to match on
"--helpmedosoemthingwithareallylongoptionname"?

暗地喜欢 2024-07-18 18:15:56

你说得对。

此外,您提供的示例将匹配“--help”,但也匹配以“--help”开头的所有内容(例如“--help-me”)。

极少数情况下,过度热心==错误。

You're right.

Moreover, the example you provided would match "--help" but also everything that begins with "--help" (like "--help-me").

A rare case in which overzealous == wrong.

扛起拖把扫天下 2024-07-18 18:15:56

据我所知,你是完全正确的——没有理由使用 strncmp 而不是 strcmp。 也许人们只是过于谨慎(不一定是坏事)。

As far as I know, you're absolutely right--there's no reason to use strncmp instead of strcmp. Perhaps people are just being overcautious (not necessarily a bad thing).

入怼 2024-07-18 18:15:56

正如其他人所说,strcmp() 与文字一起使用是完全安全的。 如果您想使用 strncmp(),请尝试以下操作:

strncmp(argv[i], "--help", sizeof("--help"))

让编译器为您进行计数!

这只会匹配确切的字符串“--help”。 如果您想要匹配以 "--help" 开头的所有字符串(如您的代码所示),请使用 sizeof() - 1 不包含最后一个 '\0'

As others have said, strcmp() is perfectly safe to use with literals. If you want to use strncmp(), try this:

strncmp(argv[i], "--help", sizeof("--help"))

Let the compiler do the counting for you!

This will only match the exact string "--help". If you want to match all strings which begin with "--help" (as your code does), use sizeof() - 1 to not include the last '\0'.

骄傲 2024-07-18 18:15:56

是的,文字的存在将比较数据的大小限制为文字的大小。 stncmp 在这里是多余的。

有些人可能会说 strncmp 是一个值得养成的好习惯,但这与计算字符的麻烦相比更重要。

Yes, the presence of literal limits the size of compared data to the size of the literal. stncmp is redundant here.

Some may say that strncmp is a good habit to get into, but this is outweighted by the trouble of counting chars.

好听的两个字的网名 2024-07-18 18:15:56

这样做可能不是为了安全。 可以只检查命令行参数的开头。 许多程序只检查命令行开关的开头而忽略其余部分。

It's probably not done for safety. It could have been done to check only the start of command line parameter. Many programs just check the beginning of the command line switches and ignore the rest.

挽你眉间 2024-07-18 18:15:56

我可能会用 C 写这样的东西(如果我经常使用 strncmp 并且不想进行字符计数):

if(... strncmp(argv[i], "--help", sizeof("--help") - 1) == 0 

I would probably write something like this in C(if I was using strncmp a lot & didn't want to do character counting):

if(... strncmp(argv[i], "--help", sizeof("--help") - 1) == 0 
戏剧牡丹亭 2024-07-18 18:15:56

呃...从技术上讲,这样的事情不可能发生吗?

char *cp1 = "help";
cp1[4] = '!'; // BAD PRACTICE! don't try to mutate a string constant!
// Especially if you remove the terminating null!
  ...
strcmp(some_variable, "help"); 
// if compiler is "smart" enough to use the same memory to implement
// both instances of "help", you are screwed...

我猜这是一个病态的案例和/或垃圾进,垃圾出(“医生,当我用头撞墙时很疼!”“那就不要这样做!”)......

(ps我是只是提出这个问题——如果你觉得这篇文章混淆视听,请适当评论,我会删除它)

er... technically couldn't something like this happen?

char *cp1 = "help";
cp1[4] = '!'; // BAD PRACTICE! don't try to mutate a string constant!
// Especially if you remove the terminating null!
  ...
strcmp(some_variable, "help"); 
// if compiler is "smart" enough to use the same memory to implement
// both instances of "help", you are screwed...

I guess this is a pathological case and/or garbage-in, garbage out ("Doc, it hurts when I whack my head against the wall!" "Then don't do it!")...

(p.s. I'm just raising the issue -- if you feel this post muddies the waters, comment appropriately & I'll delete it)

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文