2012-09-02 8 views
2

일부 오래된 코드에서 정적 분석 도구를 실행하기로 결정했는데 sprintf를 사용하고있는 곳이 많습니다. 이 도구는 sprintf가 버퍼 오버 플로우에 대한 경계 검사를 수행하지 않기 때문에 호출을 vsnprintf 또는 snprintf로 바꾸는 것이 좋습니다.snprintf 또는 vsnprintf가 더 좋으며 어떻게 안전하게 사용할 수 있습니까?

난 쉽게 그냥 발견을하고 호출에 교체 대신 현재 snprintf 또는 vsnprintf을 사용할 수 있도록,하지만 난 안전 기능을하기 위해 수행해야 할 다른 아무것도 확인 할 수 있습니다

경우에 따라 사용되는 문자열은 사용자 입력에서 비롯되며 경우에 따라 그렇지 않습니다.

누구나 올바르게 수행하는 방법에 대한 조언이 있습니까?

+7

"snprintf 또는 vsnprintf가 더 나은지 여부"는 가변 인수 또는 'va_list'여부에 따라 다릅니다. –

+0

이식성이 문제가됩니까? – robert

+0

휴대성에 대해서는 걱정하지 않습니다. – petFoo

답변

4

내가 쉽게 그냥 발견을하고 아니, 그렇게 쉬운 일이 아닙니다 대신

현재 snprintf 또는 vsnprintf을 사용하도록 호출에 교체 할 수 있습니다. snprintf 또는 vsnprintf의 정의를 살펴보면 출력 버퍼의 길이를 지정하는 size이라는 추가 인수가 표시됩니다. 기능 이름에 n의 의미입니다. 코드를 안전하게 만들려면 sprintf를 수행하는 모든 위치를 살펴보고 출력 버퍼에 쓸 수있는 최대 바이트 수를 알아 내고 size 인수를 snprintf 또는 vsnprintf으로 전달해야합니다.

안전하지 않은 코드 :

char buffer[10]; 
sprintf(buffer, "%d %d", x, y); // UNSAFE if x and y can be large 

상응하는 안전 코드 : 검색 및 대체 모든 코드는 위의 예에 맞는 경우

char buffer[10]; 
snprintf(buffer, sizeof(buffer), "%d %d", x, y); 

아마, 당신은 할 수 있습니다. 그러나 좀 더 복잡한 경우에는 아마도 그것에 대해 생각해야 할 것입니다.

+2

검색과 치환은'buffer'가 배열이 아닌 포인터 일 때 옳은 일을 할 수 없지만 포인터의 크기보다 작은 버퍼 (일반적으로 4 또는 8 바이트)를 사용하지 않는 한, 오버플로를 허용하는 것보다 출력이 과도하게 잘 리도록하십시오. 그리고 잘하면 테스트를 실행하자마자 바로 그러한 잘림 버그가 즉시 나타납니다. –

관련 문제