리눅스와 윈도우 10의 bash에서 돌아가는 프로그램이 있는데요 이 프로그램을 윈도우용으로 포팅하려고 합니다
별 프로그램은 아니고 stat이랑 open, read, write 몇 번 호출하는 간단한 프로그램 입니다
그런데 mingw 에서 stat, read 같은 함수가 return 을 -1로 합니다 퍼미션 문제인가 싶어 관리자 권한으로 실행해봤는데도 동일하네요
혹시 아시는지요?
file path를 어떻게 주셨나요?
경로에 한글이 있으면 잘 안될 수도 있어요. C:\Temp\ 밑에서 프로그램과 실험 파일을 넣고 테스트 해보세요.
모두들 행복하세요~
먼저 올렸던 질문은 경로 때문에 생기는 문제였습니다. eclipse에서 디버그 모드로 실행하면 실행파일이 있는 위치가 경로로 잡히지 않고 프로젝트 로드한 디렉토리가 경로로 잡히네요
그리고 이번에는 317KB 정도 하는 바이너리를 open 후 read하면 474B 만 읽히고 0를 리턴하는 문제가 있습니다.
1B씩 반복해서 읽거나 루프를 돌려놔도 무조건 474B 만 읽고 0를 리턴하네요 474B는 내용을 비교해보면 잘 읽는 것 같습니다. 왜 이럴까요? (코드는 별거 없습니다)
int rb; int fd = open(fname, O_RDONLY); if(fd <= 0) { return -1; } for(len=0, rb=1; len<file_length && rb>0; len++) { rb = read(fd, buf + len, 1); }
코드가 일부분 뿐이라서 확실하진 않지만
file_length 값이 474 일것 같아 보이네요. file_length 값을 먼저 확인해보세요.
read() 함수가 0을 리턴할때, errno가 EAGAIN때 20ms sleep하고 총 5회 가량 재시도 해보세요. 그리고 read() 함수를 1바이트씩 읽는 것 보다 파일 캐쉬 크기 (일반적으로 4KiB 또는 8KiB) 단위로 읽는 것이 좋습니다.
errno 는 read() 가 0 보다 작은 값을 반환할 때만 의미가 있는 값이며, EAGAIN 은 일반적으론 non-blocking I/O 때만 의미 있는 errno 이며, file I/O 크기에 대한 미신은 https://kldp.org/node/144033 읽어보시고요.
"file I/O 크기에 대한 미신"에 대해 어떤 점을 주장하고 계시는지요?
무슨 의도로 링크를 거셨는지 도무지 알 수가 없군요.
제 좁은 소견으로는, 최적의 file I/O 단위가 어느 정도인지는 상황에 따라서도 다르고 서로 이견의 여지도 있을 수 있겠습니다만,
최소한 그게 1 byte per syscall은 아닐 거라는 데 많이들 동의하시리라고 생각합니다.
그럼... 위 상황은 무슨 원인이길래 read()가 갑자기 0을 리턴하죠? (317KiB 가량의 큰 데이터를 1B씩 읽는 방식은 저라면 절대 사용하지 않을 방식입니다.)
어차피 1B씩 읽는 건 문제가 있다 싶어, 읽기 버퍼를 만들어서 read 하라고 조언했고, 그러자면 절적한 버퍼 크기를 지정해야 하는데, 그 크기를 Cache 단위 (혹은 사용자 임의) 크기로 하는 것이 좋겠다라고 했죠.
그런데 "읽기 버퍼 사용 및 버퍼 크기를 Cache 크기로 지정해라"와 "커널 Cache 시스템을 신뢰해라"는 것은 별개 사안 이고 또 그 Cache 시스템에 대한 믿음이 미신으로 치부하는 것은 지나치게 과한 주장 같습니다.
커널 Cache에 잘못된 것이 있을 수 있는데 만약에 잘못된 것을 발견하면 그걸 고쳐서 쓰던가 아니면 커널 개발(공헌)자들에게 친절히 보고해서 수정을 부탁하면 된다고 봅니다.
제가 코드를 이상하게 짜서 분란이 발생하고 있군요 죄송합니다
errno는 발생되지 않습니다(항상 0이상의 정수만 리턴) 딜레이를 넣어도 마찬가지네요 웃긴게 stat의 filesize는 정확하게 읽습니다.
mingw가 이상하다고 판단하여 플랫폼을 옮겼습니다 저 루프코드는 신경쓰지 마세요 제가 봐도 별로 안 좋게 짜여진 거 같습니다
타플랫폼으로 옮겼으니 상황이 변화되어 목적한 과업은 완수하겠지만...
그래도 현상이 이상하고 또 원인이 궁금하잖아요!?
어쨌든 원글을 올리셨는데 끝까지 원인 파악하여 결론을 내려준다면, 훗날 비슷한 일을 격을 후배들에게 도움이 되지 않을까요?
텍스트 포맷에 대한 자세한 정보
<code>
<blockcode>
<apache>
<applescript>
<autoconf>
<awk>
<bash>
<c>
<cpp>
<css>
<diff>
<drupal5>
<drupal6>
<gdb>
<html>
<html5>
<java>
<javascript>
<ldif>
<lua>
<make>
<mysql>
<perl>
<perl6>
<php>
<pgsql>
<proftpd>
<python>
<reg>
<spec>
<ruby>
<foo>
[foo]
file path를 어떻게 주셨나요?
file path를 어떻게 주셨나요?
아뇨~ 잘됩니다.
경로에 한글이 있으면 잘 안될 수도 있어요.
C:\Temp\ 밑에서 프로그램과 실험 파일을 넣고 테스트 해보세요.
모두들 행복하세요~
먼저 올렸던 질문은 경로 때문에 생기는 문제였습니다.
먼저 올렸던 질문은 경로 때문에 생기는 문제였습니다.
eclipse에서 디버그 모드로 실행하면 실행파일이 있는 위치가 경로로 잡히지 않고 프로젝트 로드한 디렉토리가 경로로 잡히네요
그리고 이번에는 317KB 정도 하는 바이너리를 open 후 read하면 474B 만 읽히고 0를 리턴하는 문제가 있습니다.
1B씩 반복해서 읽거나 루프를 돌려놔도 무조건 474B 만 읽고 0를 리턴하네요
474B는 내용을 비교해보면 잘 읽는 것 같습니다. 왜 이럴까요?
(코드는 별거 없습니다)
-> 실행하면 len은 474 가 나옴
코드가 일부분 뿐이라서 확실하진 않지만
코드가 일부분 뿐이라서 확실하진 않지만
file_length 값이 474 일것 같아 보이네요.
file_length 값을 먼저 확인해보세요.
I/O 재시도 추가 해야 할 겁니다.
read() 함수가 0을 리턴할때, errno가 EAGAIN때 20ms sleep하고 총 5회 가량 재시도 해보세요.
그리고 read() 함수를 1바이트씩 읽는 것 보다 파일 캐쉬 크기 (일반적으로 4KiB 또는 8KiB) 단위로 읽는 것이 좋습니다.
모두들 행복하세요~
errno 는 read() 가 0 보다 작은 값을
errno 는 read() 가 0 보다 작은 값을 반환할 때만 의미가 있는 값이며,
EAGAIN 은 일반적으론 non-blocking I/O 때만 의미 있는 errno 이며,
file I/O 크기에 대한 미신은 https://kldp.org/node/144033 읽어보시고요.
"file I/O 크기에 대한 미신"에 대해 어떤
"file I/O 크기에 대한 미신"에 대해 어떤 점을 주장하고 계시는지요?
무슨 의도로 링크를 거셨는지 도무지 알 수가 없군요.
제 좁은 소견으로는, 최적의 file I/O 단위가 어느 정도인지는 상황에 따라서도 다르고 서로 이견의 여지도 있을 수 있겠습니다만,
최소한 그게 1 byte per syscall은 아닐 거라는 데 많이들 동의하시리라고 생각합니다.
그럼...
그럼... 위 상황은 무슨 원인이길래 read()가 갑자기 0을 리턴하죠?
(317KiB 가량의 큰 데이터를 1B씩 읽는 방식은 저라면 절대 사용하지 않을 방식입니다.)
어차피 1B씩 읽는 건 문제가 있다 싶어, 읽기 버퍼를 만들어서 read 하라고 조언했고, 그러자면 절적한 버퍼 크기를 지정해야 하는데, 그 크기를 Cache 단위 (혹은 사용자 임의) 크기로 하는 것이 좋겠다라고 했죠.
그런데 "읽기 버퍼 사용 및 버퍼 크기를 Cache 크기로 지정해라"와 "커널 Cache 시스템을 신뢰해라"는 것은 별개 사안 이고 또 그 Cache 시스템에 대한 믿음이 미신으로 치부하는 것은 지나치게 과한 주장 같습니다.
커널 Cache에 잘못된 것이 있을 수 있는데 만약에 잘못된 것을 발견하면 그걸 고쳐서 쓰던가 아니면 커널 개발(공헌)자들에게 친절히 보고해서 수정을 부탁하면 된다고 봅니다.
모두들 행복하세요~
제가 코드를 이상하게 짜서 분란이 발생하고 있군요
제가 코드를 이상하게 짜서 분란이 발생하고 있군요
죄송합니다
errno는 발생되지 않습니다(항상 0이상의 정수만 리턴)
딜레이를 넣어도 마찬가지네요 웃긴게 stat의 filesize는 정확하게 읽습니다.
mingw가 이상하다고 판단하여 플랫폼을 옮겼습니다
저 루프코드는 신경쓰지 마세요 제가 봐도 별로 안 좋게 짜여진 거 같습니다
어차피..
타플랫폼으로 옮겼으니 상황이 변화되어 목적한 과업은 완수하겠지만...
그래도 현상이 이상하고 또 원인이 궁금하잖아요!?
어쨌든 원글을 올리셨는데 끝까지 원인 파악하여 결론을 내려준다면, 훗날 비슷한 일을 격을 후배들에게 도움이 되지 않을까요?
모두들 행복하세요~
댓글 달기