디스크 I/O 작업 할때 성능 향상을 하기 위한 방법?

hohory의 이미지

안녕하세요.

리눅스에서 프로그래밍 하고 있습니다.

빈번하게 다량의 데이터들을 file로(disk에..) write하는 작업을 하려 합니다.

그냥 막무가내로 write하는 것보다는

disk의 block size 단위로 write하는 것이 좋을 듯 한데요~

disk의 block size는 일반적으로 어떻게 되는지,

그리고 해당 시스템의 정확한 disk block size를 알아 내는 방법은 어떤 것들이 있는지 궁금합니다.

mach의 이미지

디스크 블록 사이즈는 4096바이트가 유닉스에서 일반적입니다.
(실험에 의해 결정되었음; 파일시스템관련 서적 참고)

lstat()시스템 호출로 블록 사이즈를 알 수 있습니다.(간단한 코딩으로)

블록사이즈로 출력하면 좋겠지요. 다수개 프로세스가 동시에 하나의 파일에 출력하는 형태가 아니라면, fwrite()등(fprintf... ) 사용자 수준 버퍼링 라이브러리를 사용해 보는 것도 좋겠습니다.
------------------ P.S. --------------
지식은 오픈해서 검증받아야 산지식이된다고 동네 아저씨가 그러더라.

------------------ P.S. --------------
지식은 오픈해서 검증받아야 산지식이된다고 동네 아저씨가 그러더라.

hohory의 이미지

답변 주셔서 감사합니다^^

그런데, 만약 fwrite나 fprintf를 사용한다면..

OS가 데이터를 버퍼링 하고 있다가,
disk에 데이터를 write할 때,
disk write에 적합한 size만큼씩..
그러니깐 disk block size 만큼씩 write해 주나요?

만약 OS가 그렇게 해 준다면,
fwrite나 fprintf 내부에서 관리되는 버퍼를 이용하는게 좋을거 같은데,
그렇지 않고 그냥 버퍼에 쌓인 데이터들을 막무가내로 write하는 거라면,
application level에서 disk block size에 알맞게 buffering하다가
disk write하는게 낳을거 같아서요.

질문의 핵심은,
fwrite함수나 fprintf함수를 사용하게 되면,
OS가 disk의 block size를 고려하여 buffer에 있는 것들을 write해 주나요?

park7275의 이미지

Application -> OS write ( block 4Kbyte) ; 대략 메모리..--;
-> Disk(H/W) Buffer -> Real write ( sector size : 512-1024 byte)

이런형태인듯한데..

"OS가 disk의 block size를 고려하여 buffer에 있는 것들을 write해 주나요?"

이해가 .... --;

그리고 OS는 직접적으로 Disk에 쓴다기보단.
실제 Disk에 Write는 Driver에 의해 작동합니다.
OS는 System call해서 Data넘겨주면...음...그다음은..H/W가 알아서..
(뭐 다 동일할듯도 하지만...--;)

P.S 틀린부분이..많은듯..--; (아..제가...틀린부분이 많다는 뜻..뒤에분들이 자세히...)
-------------------------------------------------
Learning...............................................
-------------------------------------------------

[KILL] 죽을각오로.........

mach의 이미지

fwrite()등을 사용하면 일단 라이브러리가(응용프로그램에 링크된) 버퍼링을 합니다. 그리고는 적절한 시점에(라이브러리 구현에 따라 틀림; 그러나, 최적화를 위해 노력했을 것으로 당연히 예측이 됩니다) 운영체제에게 넘기게 됩니다.(이때, write() 시스템호출을 사용) 운영체제는 자체적으로 버퍼캐시라는 효율을 강조한 버퍼링메카니즘을 가지고 있고, 적절한 시기에 실제 물리 디바이스 드라이버를 호출해서 디스크에 쓰게 됩니다(delayed write).

*운영체제를 손대는 입장이(또는 파일시스템을 새로이 만드는것이) 아니라면, 사용자 수준( 응용프로그램 및 라이브러리)에서 적절히, 버퍼링 메카니즘을 활용하는 것이 하나의 방법이겠지요.

------------------ P.S. --------------
지식은 오픈해서 검증받아야 산지식이된다고 동네 아저씨가 그러더라.

------------------ P.S. --------------
지식은 오픈해서 검증받아야 산지식이된다고 동네 아저씨가 그러더라.

cinsk의 이미지

수준 높은 C 라이브러리라면 당연히 disk I/O에 최적화해서 작업을 수행합니다. 그러나 이는 구현에 따라 다른 내용이므로, 모든 C 라이브러리가 무조건 그렇게 한다! 라고 할 수 있는 것은 아닙니다.

Quote:

application level에서 disk block size에 알맞게 buffering하다가
disk write하는게 낳을거 같아서요.

dd(1)를 예로 들면 좋겠네요. dd(1)는 입/출력 버퍼 크기를 지정해서, 파일을 복사/생성할 수 있습니다. 또 GNU coreutils에 포함된 cat과 같은 명령은 당연히 말씀하신 것처럼 작업을 수행합니다.

mach님이 말씀하신것처럼 효과적인 블럭 사이즈는 lstat(2) 또는 statvfs(2)로 알 수 있습니다.

--
C FAQ: http://www.eskimo.com/~scs/C-faq/top.html
Korean Ver: http://www.cinsk.org/cfaqs/

댓글 달기

Filtered HTML

  • 텍스트에 BBCode 태그를 사용할 수 있습니다. URL은 자동으로 링크 됩니다.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>
  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <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].
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.

BBCode

  • 텍스트에 BBCode 태그를 사용할 수 있습니다. URL은 자동으로 링크 됩니다.
  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <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].
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param>
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.

Textile

  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <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].
  • You can use Textile markup to format text.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>

Markdown

  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <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].
  • Quick Tips:
    • Two or more spaces at a line's end = Line break
    • Double returns = Paragraph
    • *Single asterisks* or _single underscores_ = Emphasis
    • **Double** or __double__ = Strong
    • This is [a link](http://the.link.example.com "The optional title text")
    For complete details on the Markdown syntax, see the Markdown documentation and Markdown Extra documentation for tables, footnotes, and more.
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>

Plain text

  • HTML 태그를 사용할 수 없습니다.
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.
  • 줄과 단락은 자동으로 분리됩니다.
댓글 첨부 파일
이 댓글에 이미지나 파일을 업로드 합니다.
파일 크기는 8 MB보다 작아야 합니다.
허용할 파일 형식: txt pdf doc xls gif jpg jpeg mp3 png rar zip.
CAPTCHA
이것은 자동으로 스팸을 올리는 것을 막기 위해서 제공됩니다.