2009-06-23 67 views
12

我使用的G ++中以標準FTELLFSEEK選項運行到整數溢出讀取大型文件,但我想我是錯誤的,因爲它似乎ftell64fseek64不可用。我一直在尋找,許多網站似乎使用lseek的off64_t數據類型來引用,但我還沒有發現任何實例引用的東西等於FSEEK。目前我正在閱讀的文件是16GB + CSV文件,預計至少會增加一倍。尋求和在Linux C++應用程序

沒有任何外部庫對於與fseek/ftell對實現類似結構,最直接的方法是什麼?我的應用程序現在使用4.x的標準GCC/G ++庫。

回答

24

fseek64是C函數。爲了使它可用,你必須在包含系統頭文件之前定義_FILE_OFFSET_BITS = 64這或多或少地將fseek定義爲實際的fseek64。或者在編譯器參數中執行,例如 GCC -D_FILE_OFFSET_BITS = 64 ....

http://www.suse.de/~aj/linux_lfs.html有大文件支持在Linux上有很大overviw:

  • 編譯與 「GCC -D_FILE_OFFSET_BITS = 64」 的節目。這會強制所有文件訪問調用使用64位變體。幾種類型也改變,例如off_t變成off64_t。因此,始終使用正確的類型並且不要使用例如int而不是off_t。爲了便於與其他平臺一起使用,您應該使用getconf LFS_CFLAGS,它將在Linux平臺上返回-D_FILE_OFFSET_BITS = 64,但可能會返回其他內容。 Solaris操作系統。對於鏈接,您應該使用通過getconf LFS_LDFLAGS報告的鏈接標誌。在Linux系統上,您不需要特殊的鏈接標誌。
  • 定義_LARGEFILE_SOURCE和_LARGEFILE64_SOURCE。通過這些定義,您可以直接使用像open64這樣的LFS函數。
  • 在打開時使用O_LARGEFILE標誌來操作大文件。
+0

所以,我按照你的指示,一切都在編譯文件。但我似乎仍然在溢出。你如何在fopen64中使用O_LARGEFILE參數? – 2009-06-23 23:56:38

5

fseek64()不是標準的,編譯器文檔應該告訴你在哪裏可以找到它。

您是否試過fgetposfsetpos?它們專爲大文件而設計,實現通常使用64位類型作爲fpos_t的基礎。

2

使用fsetpos(3)fgetpos(3)。他們使用fpos_t數據類型,我相信這是保證能夠保持至少64位。

3

你試過fseeko()設置爲的_FILE_OFFSET_BITS預處理符號?

這會給你一個FSEEK()樣的接口,但類型off_t的代替偏移參數。設置_FILE_OFFSET_BITS = 64將使off_t爲64位類型。

同樣爲ftello()

9

如果您想堅持ISO C標準接口,請使用fgetpos()fsetpos()。但是,這些功能僅用於保存文件位置並稍後返回到同一位置。它們表示使用類型fpos_t的位置,不要求它是整數數據類型。例如,在基於記錄的系統上,它可能是一個包含記錄中的記錄號和偏移量的結構。這可能太有限制了。

POSIX定義了函數ftello()fseeko(),它們表示使用off_t類型的位置。這需要是一個整數類型,並且該值是從文件開始的字節偏移量。您可以對其執行算術運算,並可以使用fseeko()執行相關搜索。這將適用於Linux和其他POSIX系統。

另外,用-D_FILE_OFFSET_BITS=64(Linux/Solaris)進行編譯。這會將off_t定義爲64位類型(即off64_t)而不是long,並且會將使用文件偏移量的函數重新定義爲需要64位偏移量的版本。這是您編譯64位時的默認值,因此在這種情況下不需要。