ddが2,147,479,553バイト以上を1回で処理できない話

Chrome OSVMware Toolでもインストールしてみようかと、色々と試してる過程で4GB超の空の仮想ディスクファイルを作ろうと次のコマンドを実行した。

root@ubuntu:/tmp# dd if=/dev/zero of=flash-image-flat.vmdk bs=4043308544 count=1
0+1 records in
0+1 records out
2147479552 bytes (2.1 GB) copied, 25.0769 s, 85.6 MB/s
root@ubuntu:/tmp# 

なんかメッセージが変だ? はて? 作られたファイルの大きさを見てみると、

root@ubuntu:/tmp# ls -l flash-image-flat.vmdk
-rw-r--r-- 1 root root 2147479552 2009-11-25 09:33 flash-image-flat.vmdk
root@ubuntu:/tmp#

2GB弱しかない。色々と調べていくと

root@ubuntu:/tmp# dd if=/dev/zero of=flash-image-flat.vmdk bs=2147479552 count=1
1+0 records in
1+0 records out
2147479552 bytes (2.1 GB) copied, 23.84 s, 90.1 MB/s
root@ubuntu:/tmp# ls -l flash-image-flat.vmdk
-rw-r--r-- 1 root root 2147479552 2009-11-25 09:34 flash-image-flat.vmdk

これはOK。でも

root@ubuntu:/tmp# dd if=/dev/zero of=flash-image-flat.vmdk bs=2147479553 count=1
0+1 records in
0+1 records out
2147479552 bytes (2.1 GB) copied, 28.1609 s, 76.3 MB/s
root@ubuntu:/tmp# ls -l flash-image-flat.vmdk
-rw-r--r-- 1 root root 2147479552 2009-11-25 09:35 flash-image-flat.vmdk
root@ubuntu:/tmp#

これはNG。どうも2147479553バイト以上は1回の読み込みで処理できないようだ。2147479552バイトというのは、2GB(2147483648)-4096=2147479552。64bit版のUbuntuを使っているのに何で2GBまで? mallocにこんな制限があったっけ? それともddの仕様?

多分、int(32bit singed)を使っているためだろうと思うが、こういう御時世になるとintの制限というのは思わぬところにも出てくる。主記憶が高々1GBの時代であれば、こんなddの使い方は考えられなかっただろうから、こんな仕様になっていても仕方ないか。最近ではエントリクラスのPCでもメモリ2GB以上は当たり前になている来ているし、フラッシュメモリ等も16GBとかが一般的になって来ている時代に1回で2GB以上の処理ができないのは寂しいが。(例えば、PCのスペックが1,000倍位低かった15年位前、主記憶が32MBでHDDも1GB位の10年前であれば1回で2MB以上の処理が出来ないというコマンドはちょっと寂しい感じがしたことだろう。)

ということで、4043308544バイトのファイルを作るには、2147479552バイト以下で複数回書き込む必要がある。まず、作るファイルのサイズを素因数分解して2147479552バイト以下の最大の(もしくは適当な)約数を探す。その上で、複数回を指定する、という方法になる。

root@ubuntu/tmp# factor 4043308544
4043308544: 2 2 2 2 2 2 2 2 2 11 717917
root@ubuntu/tmp# expr 4043308544 / 4
1010827136
root@ubuntu/tmp# dd if=/dev/zero of=flash-image-flat.vmdk bs=1010827136 count=4
4+0 records in
4+0 records out
4043308544 bytes (4.0 GB) copied, 56.8931 s, 71.1 MB/s
root@ubuntu/tmp# ls -l flash-image-flat.vmdk
-rw-r--r-- 1 root root 4043308544 2009-11-25 09:44 flash-image-flat.vmdk
root@ubuntu/tmp#