2014-12-14 5 views
-2
#include<stdio.h> 
#include<conio.h> 
int main() 
{ 
char test [7]; 
for(int i=0;i<10;i++) 
scanf("%c",&test[i]); 
puts(test); 
getch(); 
return 0; 
} 

DevC++ (대학교 규칙)를 사용하고 있으며 gets()에 경계 체크가 없으므로 의도적으로 for() 루프를 사용하여 문자열을 입력하는 것으로 알고 있습니다. 배열의 크기보다 큰 문자열을 입력 할 때 puts는 여분의 문자를 인쇄합니다. 왜 그렇게?왜 puts()는 끝에 여분의 문자를 인쇄합니까?

샘플 입력 : helloworld를 출력 : hellowos

샘플 입력 : Hellopeople 출력 : 메모리를 범람하고 있기 때문에 Hellopep

+0

'가져 오기'가 없으므로이 기능이 존재했는지 잊어 버려주세요. OTOH'fgets'는 생존하고 있습니다. 그리고 손으로 쓰는 루프 대신에 그것을 사용해야합니다. NUL 캐릭터로 문자열을 종료하는 것을 주저하지 않았습니다. 또한 최대 10 자의 7 자 긴 버퍼를 의도적으로 오버플로하는 것은 무엇입니까? –

+1

UB multi-dupe입니다. 배열 범위를 오버런하지 말고 SO가 검색 가능하다는 점에 유의하십시오. –

+0

@ n.m. 의도적 인 오버플로는 오버 플로우의 경우 puts의 동작을 확인하는 것이 었습니다. puts()가 단지 8자를 인쇄해야하는 이유를 설명 할 수 있습니까? 7. 인쇄 된 문자가 바로 다음에 나오는 이유는 무엇입니까? –

답변

2

그것은이다. 귀하의 배열은 7 자 충분가 있고 10로 채우하려고 :

char test [11];   // Array indexes 0-10 allowed. 
for(int i=0;i<10;i++)  // Array indexes 0-9 used. 
    scanf("%c",&test[i]); 
test[10] = '\0';   // And add string terminator before puts(). 

당신이 원하는 경우

char test [7];    // Array indexes 0-6 allowed. 
for(int i=0;i<10;i++)  // Array indexes 0-9 used. 
    scanf("%c",&test[i]); 

당신은 같은과 (문자열 종결을 허용 포함)를 해결할 수 있습니다 버퍼 오버플로 보호 기능이있는 강화 된 사용자 입력 함수 인 경우 일반적으로 fgets()에서 빌드 된 것이 일반적으로 표준 C에서 가장 좋은 방법입니다. 예를 들어 this과 같은 것입니다.

0

test 배열은 for 루프를 통해 10 개의 문자를 읽는 동안 단 7 개의 문자입니다. 이것은 추락 할 수 있습니다.

puts 또한 문자열이 0으로 종료 될 것으로 예상됩니다. 문자 뒤에 0을 명시 적으로 넣지 않으므로, 출력에는 0 바이트가 될 때까지 문자 뒤에 오는 가비지가 포함됩니다.

1

당신이 그 수에 가장 상점 7 개 요소

char test [7]; 
for(int i=0;i<10;i++) 
    scanf("%c",&test[i]); 

당신은 그것을 9 저장 할 수 있도록 (버퍼 (10) 요소를 만들어이 문제를 해결할 수있는 버퍼에 10 개 개의 문자를 저장하려고으로 당신은 buffer overflow이 문자와 마지막에 \0 하나)이 사용 :

char test [10]; //10 elements long 
scanf("%9s",test); //Get at-most 9 chars 

또는 당신이 너무 fgets를 사용할 수 있습니다.

0

문자열이 '\ 0'으로 끝나지 않습니다.