简体   繁体   English

与sscanf_s混淆

[英]Confusion with sscanf_s

I am having issues with sscanf_s, essentially I have this line of code: 我遇到了sscanf_s的问题,基本上我有这行代码:

sscanf_s( line.c_str(),
          "<float_array id=\"%*s[^\"]\" count=\"%*d\">%[^<]s",
          numString);

I am feeding it this line of text: 我正在给它提供这一行文字:

<float_array id="Cube-mesh-positions-array" count="24">1 1 -1 1 -1 -1 -1 -0.9999998 -1    -0.9999997 1 -1 1 0.9999995 1 0.9999994 -1.000001 1 -1 -0.9999997 1 -1 1 1</float_array>

What I am trying to achieve is read the number array written after count="24"> and pass it to another function, however numString remains with a value of "" after being passed through the equation, therefore causing the subsequent functions to fail. 我想要实现的是读取在count="24">之后写入的数字数组并将其传递给另一个函数,但是在通过等式之后numString保持值为"" ,因此导致后续函数失败。 if anyone could offer me insight into why this is occurring I would be very appreciative. 如果有人能让我深入了解为什么会发生这种情况,我将非常感激。

A short SSCCE that I have tested has revealed that the problem lies elsewhere, I shall have to investigate this further - sorry for wasting your time, and thank you for taking your time to try and help me. 我测试的一个简短的SSCCE显示问题出在其他地方,我将不得不进一步调查 - 抱歉浪费你的时间,并感谢你花时间去尝试帮助我。

The function sscanf_s is a Microsoft invention, intended to be "more secure" than the standard sscanf function. 函数sscanf_s是Microsoft的发明,旨在比标准的sscanf函数“更安全”。

As such, if you are using "%s" or "%c" , it requires two parameters: One being the buffer to write the input to, and an integer specifying the available size of the buffer , so that a long input string does not result in a buffer overflow. 因此,如果您使用"%s""%c" ,则需要两个参数:一个是写入输入的缓冲区, 一个是指定缓冲区可用大小的整数 ,因此长输入字符串可以不会导致缓冲区溢出。

Unfortunately this is not quite that obvious to users of the function (like yourself), resulting in frequent mis-use of the function (which somewhat reduces the "security" implied). 不幸的是,这对于函数的用户来说并不那么明显(像你自己),导致频繁使用该函数(这有点降低了隐含的“安全性”)。

Link to the Microsoft docs ; 链接到Microsoft文档 ; refer to the section "remarks". 请参阅“备注”部分。

So what you have here is undefined behaviour, as sscanf_s attempts to read an integer from the stack where you haven't put one. 所以你在这里有未定义的行为,因为sscanf_s试图从堆栈中读取一个你没有放置的整数。 You end up lucky that the memory read is apparently zero, so zero bytes are written to numString . 你最终很幸运,内存读取显然是零,所以零字节写入numString

This should do nicely: 这应该做得很好:

size_t BUFSIZE = 50;
char numString[ BUFSIZE ];
sscanf_s( line.c_str(),
          "<float_array id=\"%*s[^\"]\" count=\"%*d\">%[^<]s",
          numString, BUFSIZE );

Note that numString better actually be a char[] . 需要注意的是numString更好的实际上一个char[] Your question was initially tagged as C++; 您的问题最初标记为C ++; if numString is actually a std::string , be advised that you cannot use the scanf family function with std::string parameters. 如果numString实际上是一个std::string ,请注意你不能将scanf系列函数与std::string参数一起使用。


(Sorry for the edits, got it wrong the first few times. That format string is something... ;-) ) (抱歉编辑,前几次弄错了。那格式字符串是...... ;-))

char numString[ 256 ];
sscanf_s( line.c_str(),
          "<float_array id=\"%*[^\"]\" count=\"%*d\">%255[^<]",
          numString, 256);

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM