我正在编写操作系统,并且在创建printf()
函数方面遇到了问题。
当通过确定存在%的switch语句并且现在正试图弄清楚下一个字符是什么时,会发生这种情况:
print(string str)
会将字符串str打印到stdout
(但不包含%x,%d,%s等)。
itoa(int n, string str, const uint8_t base)
会将int转换为指定基数的字符串。
case 'i':
case 'd': { // interger
const string str =
itoa(
va_arg(args, int),
str, 10);
print(str);
i++;
break;
}
case 'X':
case 'x': { // hexidecimal
const string str2 =
itoa(
va_arg(args, int),
str2, 16);
print("0x");
print(str2);
i++;
break;
}
%d和%i完全按照预期应用,但如果输入因某种原因小于16,%x将无法正常工作。但奇怪的是如果我注释掉处理%d和%i的部分,%x就可以了。我不知道为什么会这样。我试过切换d和x做什么等等,但没有任何效果。我也尝试确保所有其他功能都正常工作,而且它们都是。
如果有人想看到完整的代码,请点击这里:
strLen(string str)
找到字符串str的长度。
printch(char c)
打印一个字符c。
void printf (const string format, ... )
{
const size_t length = strLen(format);
va_list args;
va_start (args, format);
// print every character in string
for (size_t i=0; i < length; i++)
{
// percent signals special functionality
if (format[i] == '%')
{
switch (format[i+1])
{
case '%': // "%%" = %
printch('%');
break;
case 'i':
case 'd': { // interger
const string str =
itoa(
va_arg(args, int),
str, 10);
print(str);
i++;
break;
}
case 'x': { // hexidecimal
const string str2 =
itoa(
va_arg(args, int),
str2, 16);
print("0x");
print(str2);
i++;
break;
}
case 'c': // character
printch(
va_arg(args, char));
i++;
break;
case 's': // string
print(
va_arg(args, string));
i++;
break;
default:
i++;
break;
}
}
else printch(format[i]);
}
va_end (args);
}
有谁知道这里发生了什么以及如何解决?请帮忙!
答案 0 :(得分:1)
当评论出不相关的代码使得代码有问题&#34;工作&#34;时,您可以确定您正在查看未定义的行为。你的代码并没有真正&#34;工作&#34 ;;它不会导致在输出中出现错误。
在您的情况下,问题似乎与您传递给itoa
的缓冲区有关:您正在向其传递一个空字符串,而不是传递缓冲区。您应该将一个小缓冲区传递给itoa
,然后才能从中构造一个字符串,如下所示:
char buf2[17];
itoa(va_arg(args, int), buf2, sizeof(buf2));
const string str2(buf2, sizeof(buf2));