2017-12-11 11 views
1

dirent 구조체에서 파일 이름을 가져 와서 모든 이름 목록을 연결된 문자열로 클라이언트에 보냅니다.C : 어떻게 파일 이름 목록을 소켓에 문자열로 보낼 수 있습니까?

숫자를 알아 내려고 몇 시간이 지난 후에도 메모리를 올바르게 할당하거나 제대로 읽을 수없는 것 같습니다. 말도 안되는 문자열이 다시 나타납니다. 따라서 생각이 들더라도 메모리를 잘못 읽어야합니다. 서버에서

void send_file_list(int socketNumber) 
{ 

    DIR *mydir; 
    if ((mydir = opendir("upload")) == NULL) { 
    perror("error"); 
    exit(EXIT_FAILURE); 
    } 

    struct dirent *entry = NULL; 

    size_t len; 

    //loop through entry to get size of all filenames as string. 
    while ((entry = readdir(mydir)) != NULL) 
    { 
    len = len + strlen(entry->d_name); 
    } 

    char filelist[len]; 

    //returns NULL when dir contents all processed 
    while ((entry = readdir(mydir)) != NULL) 
    { 
    strcat(strcat(filelist, entry->d_name),"\n"); 
    } 

    closedir(mydir); 

    size_t n = len; 

    writen(socketNumber, (unsigned char *) &n, sizeof(size_t)); 
    writen(socketNumber, (unsigned char *) filelist, n); 

    printf("Sent file list of size %zu bytes\n",n); 

}//end send_file_list() 

가져 오기 문자열 :

나는 클라이언트에

보내기 문자열,

여기

내가 지금까지 한 일이다 "\ 0"로 문자열을 추가했습니다

witen() 및 readn()은 가져온 파일 rdwrn.c 및 .h에서 가져온 것입니다.이 파일은 교과 과정 프로젝트의 일부로, 어떻게 작동하는지 완전히 모르지만 기본적으로 지정된 파일에서 읽고 쓸 수 있습니다. 소켓. 나는 그들을 만들지 않았다.

몇 시간 째 계속 지켜 봤는데 지저분 해졌습니다. 이 작업을 수행하는 더 좋은 방법이 있습니까?

+1

컴파일 시간 경고가 있습니까? BTW, 파일 이름을 분리하는 데 사용되는'\ n '때문에 당신이 예약 한 문자가 더 많아서 정의되지 않은 동작이 발생합니다. –

+0

@Serge Ballesta Complier 시간 경고 없음 –

+2

길이를 얻기 위해 readdir()을 사용하여 파일 목록을 읽은 다음 목록을 처리하기 위해 readdir()을 다시 시도합니다 ... 디렉토리 스트림을 닫아야합니다. closedir() 및 opendir()을 다시 사용하기 전에 다시 사용하십시오. 둘째, "길이"계산에서 쉼표 또는 줄 바꿈과 같은 "분리 기호"를 허용하지 않습니다. – TonyB

답변

0

이 루프 :

while ((entry = readdir(mydir)) != NULL) 
{ 
len = len + strlen(entry->d_name); 
} 

은 몇 가지 문제가 있습니다.

1) 게시 된 전체 코드에 대한 일반 사항, 들여 쓰기가 일관되지 않습니다. 일관성을 위해 모든 여는 중괄호 '{'다음에 들여 쓰기. 모든 닫는 중괄호 '}'앞에서 들여 쓰기를하지 않습니다. 각 들여 쓰기 수준을 4 칸 제안하십시오.

2) 디렉토리 항목에는 많은 종류의 항목이 있습니다. (링크, 하위 디렉토리 등)

결과 문자열에 특정 '파일 이름'을 포함하기 전에. 사용하는 것이 좋습니다, len 초기화되지 않습니다 : 코드는 정상 파일과 파일의 이름이 변수가 ...

==== 아닙니다 보장하는 항목의 종류를 확인해야

size_t len = 0; 

==== 참고 그 문자열의 끝에 NUL 바이트 오프셋 (오프셋 (offset)이 아닌, 0에서 1을 시작) 따라서 실제 길이는 1 바이트 이상

이다 리턴 strlen() 함수 = === T 그는이 코드가 현재 디렉터리 파일 이름 만 수집 할 것인지 아니면 하위 디렉터리에 파일 이름을 포함시킬 것인지 질문하지 않습니다.

==== 질문의 제목 : 파일 이름이 함께 걸리거나 공백이나 쉼표로 구분됩니까? 공백으로 구분 된 경우 공백이 포함 된 파일 이름은 무엇입니까?

==== BTW : 함수 이름은 writen()readn()에서 비롯됩니까?

+0

witen() 및 readn()은 가져온 파일 인 rdwrn.c 및 .h에서 가져온 것입니다.이 파일은 교과 과정 프로젝트의 일부로, 어떻게 작동하는지 완전히 모르지만 기본적으로 지정된 소켓에서 읽고 쓰게됩니다. 나는 그들을 만들지 않았다. –

+0

그 세부 사항은 코멘트가 아닌 질문의 텍스트에 언급되어 있어야합니다. – user3629249

+0

죄송합니다. 지금 추가하겠습니다 ... –