Gần đây, tôi nhận thấy một trường hợp kỳ lạ Tôi muốn xác minh:Số ký tự cho đến nay trong snprintf
By SUS, cho %n
trong một chuỗi định dạng, tương ứng int
sẽ được thiết lập để các-lượng-of-byte -kết quả đầu ra. Ngoài ra, đối với snprintf(dest, 3, "abcd")
, dest
sẽ trỏ đến "ab\0"
. Tại sao? Vì không có nhiều hơn n (n = 3) byte được ghi vào đầu ra (bộ đệm dest
).
Tôi suy luận rằng cho mã:
int written;
char dest[3];
snprintf(dest, 3, "abcde%n", &written);
written
sẽ được thiết lập để 2 (chấm dứt vô loại trừ khỏi count). Nhưng từ thử nghiệm tôi đã thực hiện bằng GCC 4.8.1, written
được đặt thành 5. Tôi có hiểu sai tiêu chuẩn không? Nó là một lỗi? Đó là hành vi không xác định?
Edit:
@wildplasser nói:
... hành vi của% n trong chuỗi định dạng có thể không xác định hoặc thực hiện được xác định ...
Và
... việc triển khai phải mô phỏng xử lý chuỗi định dạng hoàn chỉnh (bao gồm% n) ...
@par nói:
written
là 5 vì đó là bao nhiêu ký tự này sẽ được ghi tại điểm%n
đang gặp phải. Đây là hành vi đúng.snprintf
chỉ bản lên đếnsize
nhân vật trừ null dấu ...
Và:
Một cách khác để xem xét điều này là
%n
sẽ không có thậm chí đã gặp phải nếu nó chỉ xử lý lên đến 2 ký tự, do đó, nó có thể tưởng tượng để mong đợiwritten
để có một giá trị không hợp lệ ...
Và:
... toàn bộ chuỗi được xử lý qua
printf()
quy tắc, sau đó tối đa độ dài được áp dụng ...
Nó có thể được xác nhận là tiêu chuẩn, một tiêu chuẩn dự thảo hoặc một số nguồn chính thức?
Có vẻ như một lỗi (trong việc triển khai thư viện) với tôi. – pmg
Tôi hy vọng bạn nên * đầu tiên * nhìn vào returnvalue từ snprintf(). Các "tác dụng phụ" là khác nhau; hành vi của '% n' trong chuỗi định dạng có thể là undefined hoặc implementation được định nghĩa nếu returnvalue là> = đối số thứ 2. Trong mọi trường hợp, việc triển khai phải * mô phỏng * xử lý chuỗi định dạng * hoàn thành * (bao gồm '% n') để có được giá trị trả về chính xác, do đó tác dụng phụ có thể thu được khi đang di chuyển. – wildplasser