1

sprintf組み込みシステム (Libelium Waspmote、Arduino に似ています) で、sprintf がフォーマット指定子で指定されたよりも多くの文字を出力しているという奇妙な問題が発生しています。この特定の例%02Xでは、配列内のバイトの 16 進値を出力するために使用しています。ただし、一部のバイトでは、2 文字を書き込む代わりにFF、実際のバイト値の前にプレフィックスを付けて 4 文字が書き込まれます。snprintf指定されたバッファーサイズを尊重し、プレフィックスを出力することを除いて、同様に動作します。

参考までに、配列の内容を出力するコード スニペットを次に示します。

char *pduChars = (char *) malloc(17*sizeof(char));
pduData.toChar(pduChars);
for (int i = 0; i < 17; i++) {
    char asciiCharsS[5];
    char asciiCharsSN[3];
    int printedS = sprintf(asciiCharsS, "%02X", pduChars[i]);
    int printedSN = snprintf(asciiCharsSN, 3, "%02X", pduChars[i]);
    USB.print(printedS);
    USB.print(" ");
    USB.print(printedSN);
    USB.print(" ");
    USB.print(asciiCharsS);
    USB.print(" ");
    USB.print(asciiCharsSN);
    USB.println(" ");
}

そして、そのスニペットからの出力 (誤ったバイトのみに要約): 実際のバイト シーケンスは 0x00 0xFC 0xFF 0xFF 0x48 0xA5 0x33 0x51 である必要があります。

sprintf snprintf sprintf Buffer snprintf Buffer

…<br> 2 2 00 00
4 4 FFFC FF
4 4 FFFF FF
4 4 FFFF FF
2 2 48 48
4 4 FFA5 FF
2 2 33 33
2 2 51 51

ここで何かを見落としているのでしょうか、それとも の実装に関連するプラットフォーム固有の問題s(n)printfでしょうか?

4

3 に答える 3

5

あなたの実装は符号付き文字を使用していると思います。この形式は、符号なし"%X"の値を想定しています。キャストするか、代わりに使用します。unsigned char

/* cast */
int printedS = sprintf(asciiCharsS, "%02X", (unsigned char)pduChars[i]);
int printedSN = snprintf(asciiCharsSN, 3, "%02X", (unsigned char)pduChars[i]);

また

/* use unsigned char */
unsigned char *pduChars = malloc(17); /* cast is, at best, redundant */
                                      /* sizeof (char) is, by definition, 1 */
于 2013-03-04T12:53:14.910 に答える
2

使用している書式指定子修飾子は、パディングにのみ使用されます。値の記号の数が指定された値を超える場合、文字列全体が出力されます。

于 2013-03-04T12:46:05.273 に答える
1

%02X はパディング用です...省略されません...したがって、値が指定された値より大きい場合、文字列全体が出力されます

于 2013-03-04T13:00:14.857 に答える