状況:UbuntuのMatlabのOut of Memory
エラーを修正
目標:外部HDD/SSDに仮想メモリやスワップを割り当てます。読み取り/書き込みが20 GBpsから0.1 GBpsに減少しました。
用語:スワップと仮想メモリ here
いいえ、スワップと仮想メモリは完全に異なります。たとえば、1GBファイルのメモリマッピングでは、追加の1GBの仮想メモリが使用されますが、スワップの使用に変更はありません。スワップは、バッキングストアの一種です。仮想メモリの多くの用途は、バッキングストアとは何の関係もありません。 (また、仮想メモリがあり、スワップがないシステム、およびスワップはあるが仮想メモリがないシステムがあります。)
消費者のハードウェアは限られているため、より多くの仮想メモリを使用するか、外部HDDとスワップする必要があります。 Matlabはスワップメモリについて述べています(仮想メモリを除くTODO?)
Linuxシステム—
mkswap
およびswapon
コマンドを使用して、スワップ領域を変更します。
システムの特徴
swapon -s
でどれだけ持っているかを見ることができます
Filename Type Size Used Priority
/dev/sda3 partition 8326140 0 -1
Matlabの構成
% https://stackoverflow.com/a/35971040/54964
com.mathworks.services.Prefs.setIntegerPref('JavaMemHeapMax', 2048); % MB
% TODO cannot find ways how to put Matlab use /dev/sda3
だから、あなたは私のMatlabがそれを使用していないことがわかります。 Matlabで大きな行列でOut of Memory
エラーを受け取りました。行列をベクトルにreshape
'して、並列コードを書くことに失敗しました。ですから、作業を完了する必要があるため、仮想メモリを使用します。レートは関係ありません。
擬似コード
Sudo swapon -a
を使用するには?状況:環境のセットアップ(1)、Matlabの実行(2)、および環境のクローズ(3)のエラーを制御できません
脚本
#!/usr/bin/env bash
# https://stackoverflow.com/a/69808/54964
set -e
# TODO How to do swapoff if any error?
SWAP_FILE="/media/masi/SamiSwapVirtual/.swap_file_20.7.2016"
SIZE_MB=16000
TO_RUN="matlab"
dd if="/dev/zero" of=${SWAP_FILE} bs="1M" count=${SIZE_MB} status="progress"
mkswap ${SWAP_FILE}
chmod 0600 ${SWAP_FILE}
Sudo chown 0.0 ${SWAP_FILE} # https://unix.stackexchange.com/a/297153/16920
Sudo swapon -v ${SWAP_FILE}
echo "Swap enabled. Press enter to continue"; read
${TO_RUN}
echo "I will remove the swap. Press enter to continue"; read
Sudo swapoff -v ${SWAP_FILE}
rm -vf ${SWAP_FILE}
Transcend 25M3を使用したイテレーション1 1 TBはほとんど使用せず、ファイルシステムext4
スクリプト開始後のログ
sh start_matlab_with_swap.sh
16000+0 records in
16000+0 records out
16777216000 bytes (17 GB, 16 GiB) copied, 134.489 s, 125 MB/s
Setting up swapspace version 1, size = 15.6 GiB (16777211904 bytes)
no label, UUID=48c2835b-4499-4534-aa49-0648e15bd5d9
[Sudo] password for masi:
swapon /media/masi/SamiWeek/tmp/swap_file_18.7.2016
swapon: /media/masi/SamiWeek/tmp/swap_file_18.7.2016: insecure file owner 1000, 0 (root) suggested.
swapon: /media/masi/SamiWeek/tmp/swap_file_18.7.2016: found swap signature: version 1d, page-size 4, same byte order
swapon: /media/masi/SamiWeek/tmp/swap_file_18.7.2016: pagesize=4096, swapsize=16777216000, devsize=16777216000
Swap enabled. Press enter to continue
start_matlab_with_swap.sh: 11: read: arg count
クライアントを実行する
コマンド履歴は、スワップメモリ(チケット#02075943)でMatlabの最初の起動時に失われ、エラーが発生しました-コマンド履歴の読み取りに問題がありました--。 Matlabを再起動するだけで、デフォルト設定があれば問題は解決します。コマンドprefdir
は、デフォルトの場所である/home/masi/.matlab/R2016a
を提供します(/home/{username}/.matlab/R2016a
。再起動後にファイル/home/masi/.matlab/R2016a/matlab.prf
が存在します here 。
... [その他のエラー] ...
ターミナルでMatlabを閉じてパスワードをもう一度入力する
[Sudo] password for masi:
swapoff /media/masi/SamiWeek/tmp/swap_file_18.7.2016
[ bugs here! ]
オープン:エラートラップのより良いエラー処理をここに適用する方法は?ソースの例については、スクリプトを参照してください。スレッド エラー/警告の場合のエラートラップとスワップオフの方法
スワップのセットアップ
# https://unix.stackexchange.com/q/297767/16920
masi@masi:~$ Sudo fallocate -l 20G /mnt/.swapfile
masi@masi:~$ Sudo mkswap /mnt/.swapfile
Setting up swapspace version 1, size = 20 GiB (21474832384 bytes)
no label, UUID=45df9e48-1760-47e8-84d7-7a14f56bbd72
masi@masi:~$ Sudo swapon /mnt/.swapfile
swapon: /mnt/.swapfile: insecure permissions 0644, 0600 suggested.
masi@masi:~$ Sudo chmod 600 /mnt/.swapfile
masi@masi:~$ free -m
total used free shared buff/cache available
Mem: 7925 1494 175 196 6255 5892
Swap: 28610 0 28610
永続的な変更を行うには、/etc/fstab
の最後に次を入力します
# https://unix.stackexchange.com/a/298212/16920
# https://unix.stackexchange.com/a/298543/16920
# If swap is on SSD, trim blocks each time at startup.
#/mnt/.swapfile none swap defaults,discard 0 0
# If swap on External HDD, just use sw.
/media/masi/SamiWeek/.swapfile none swap sw 0 0
システム:Linux Ubuntu 16.04 64ビット
Linuxカーネル:4.6
Linuxカーネルオプション:wl
Matlab:2016a
Matlabの公式ドキュメント: 「メモリ不足」エラーの解決
外付けHDD:Transcend 1 TB StoreJet 25M3 review 、Transcend 2 TB StoreJet 25M3
外部HDDファイルシステム:ext4
外部HDDバッファー:8 MB
関連スレッド: buntuでMATLABメモリの制限を増やす方法は? (MATLABのmkswap、swaponの使用方法) 、 Matlabで物理メモリの増加を減らす方法? 、 Matlabでメモリ不足エラーを解決する方法 、 10800x10800マトリックスのMatlabでメモリ不足エラーを修正する方法 、 Matlab r2012bでメモリ制限(連続および全体)を増やす方法 、 Matlab 2009bで配列ブロックを増やしてメモリ不足エラーを解決する方法 、 Matlabの小さな変数のこのメモリ不足問題を解決する方法? 、 'Out of memory 'Matlabで。遅いが永続的な解決策?
OK、かなりのリストがあります。インラインで返信させてください
私はこのスクリプトのコンセプトがまったく好きではありません。スワップとして使用しようとしている外付けハードドライブがあることは悪い考えです。定期的にこれを行うつもりであれば、パーティションのサイズを変更して適切なスワップパーティションを配置するか、スワップファイルを追加するか、より大きな内部ディスクを購入してください。
数学をやるだけです。プログラムが開始される前にマトリックスのサイズがわかっている場合は、MiBでサイズを計算し、使用可能なスワップと比較します。
matlabにはAPIがありますか?これがその質問にふさわしいフォーラムだとは思いません。 APIを使用している場合でも、スワップを介してIOをブロックするため、実際の現実を反映しないぎこちないプログレスバーになります。
あなたはしません。計算が終わったからといって、オペレーティングシステムが割り当てたリソースで完了したわけではありません。スワップへの書き込みが完了すると、解放されます。あまりにも多くのメモリを消費しているため、多くのアプリケーションが必要なメモリを取得できないため、スワップも使用しています。そのままにして、オペレーティングシステムに任せてください。次の実行を実行する前に、キャッシュをクリアします。
echo 3 > /proc/sys/vm/drop_caches
おそらくそれ以上のことがあります。私はLinux VMの専門家ではありません。 SLAB/SLUBアロケーターがどのように機能し、大容量のメモリ要件に合わせてどのように調整するかを調査する価値があります。 matlabをメモリにMLOCKできる場合があります。これにより、OSがメモリを強制的に予約するか、起動しないだけで、完了したらロックを解除する必要があります。私はC APIでこれをうまく行うことができますが、再コンパイルできないプロセスの外でそれをどのように行うのかわかりません。
最後に、これはEC2が作成したものです。必要なのは16Gで、m4.4xlargeには1時間あたり0.958ドルで64GのRAMが搭載されているようです。それはカップコーヒーより少ない。ジュジュチャームなどを使用してmatlabのインストールのスクリプトを作成し、すべてをサービスとして計算に変換します。
16Gは16 GBですか?
「100 GBを超えるマトリックスが必要です。EC2で実行できるかどうかわかりません。」
echo 3 > /proc/sys/vm/drop_caches
でもキャッシュをクリアする必要がありますか?
Matlabをメモリにロックするにはどうすればよいですか?
man mlock
。それを引用したとき、私は馬鹿げたが。この呼び出しにより、必要なすべてのメモリを割り当てて、スワップアウトされないようにすることができます。仮想メモリは使用されません。それはあなたが望むものではありません。C APIをMatlabにバインドできると思います。 --プロセスに何らかの障害がある場合、スワップをオフにする考えはありますか?
OSにメモリアドレススペースを要求すると、常に成功しない場合があります。これは、再試行できないという意味ではありません。 matlabがmallocを2回呼び出すことを理解できないのは、matlabの問題です。
したがって、必要な変更に影響を与えるには、その100Gのスペースが本当にプレミアムである場合、オペレーティングシステムにどのように伝えるかを理解する必要があります。メモリフットプリントを(スターターのキャッシュをクリアすることで)トリミングし、メモリマネージャが提供された追加のスワップスペースを使用する必要性を感じないようにします。その後、その場合にのみ、メモリマネージャにスワップファイルを解放するように依頼できます。
メモリやディスクのようなものを成長させるのは簡単ですが、それらを縮小するのははるかに困難です。縮小により、そのスペースにリソースが割り当てられているすべてのユーザーの再バランスが強制されます。代わりに「100TBのストレージアレイはあるが、今では60TBしか必要ないのに、アレイの動作が停止するのは40TBのディスクを取り外すとどうしてですか?」さて、答えは明らかですよね?
だから私はそれを見るようにあなたのオプションがあります。
matlab C APIを調査して、これらの大規模なワーキングセットにメモリを割り当てる方法をより適切に制御できるかどうかを確認してください。
サブマトリックスまたはその他のスパースデータ表現を使用して、現在の計算をリファクタリングします。
膨大な数の線形代数ライブラリを使用してC/C++で独自のプログラムを作成し、計算を実行し、malloc
またはmmap
anonymousを使用して必要なアドレス空間を割り当てます。
ソフトウェア専用のスワップはできません。できることは、スワップを作成し、MATLABを起動し、MATLABの終了時にスワップを削除するシェルスクリプトを作成することです。
以下は、/ tmpディレクトリに10Mbのスワップを作成し、マウントし、Rを開始し(matlabがありません)、Rが終了するのを待って、スワップファイルをアンマウントして削除するスクリプトの例です。
次のことに注意してください。-スワップファイルはルートによって所有されていないため、警告が表示されます。これは、システムが何らかのソフトウェアを使用している場合、おそらくあなたが実行していない場合に使用し、このファイルを読むことができるからです...私はあなたにそれを修正させます。 -[ctrl]-[c]スクリプト、またはログオフなどを行う場合、スワップはマウントされたままになります。私もあなたにそれを修正させます。
#!/usr/bin/env bash
SWAP_FILE=/tmp/my_swap_file
SIZE_MB=10
TO_RUN="R"
dd if=/dev/zero of=${SWAP_FILE} bs=1M count=${SIZE_MB}
mkswap ${SWAP_FILE}
chmod 0600 ${SWAP_FILE}
Sudo swapon -v ${SWAP_FILE}
echo "Swap enabled. Press enter to continue"; read
${TO_RUN}
echo "I will remove the swap. Press enter to continue"; read
Sudo swapoff -v ${SWAP_FILE}
rm -vf ${SWAP_FILE}
少なくともRAM(zramカーネルモジュール、カーネルバージョン3.14以降で使用可能)のパフォーマンスをテストします。
modprobe zram
echo lz4 > /sys/block/zram0/comp_algorithm
echo 4G > /sys/block/zram0/disksize
mkswap --label zram0 /dev/zram0
swapon --priority 100 /dev/zram0
私の推測では、圧縮されたRAMはディスクI/Oよりも速いはずです。
再起動後も変更を維持するには、/etc/rc.local
に起動時コマンドを配置し、Sudo systemctl enable rc-local.service
を実行します。
これは、外付けハードドライブを使用してSWAPメモリを拡張する方法です。
まず、次を実行して実際のSWAPメモリを書き留めます。
free -m
次に、HDDのフォルダーを手元に用意します。 /media/myhdd
のようなものでなければなりません。
ターミナルで次のコマンドを使用して、サイズXGBのファイルを作成します。
dd if=/dev/zero of=/media/myhdd/swapfile bs=4096 count=Z
以下を使用して、ファイルにSWAPを作成します。
Sudo mkswap /media/myhdd/swapfile -f
最後に、SWAPを有効にします。
Sudo swapon -p 1000 /media/myhdd/swapfile
これでSWAPが増加しました。 free -m
でもう一度確認してください
非対話型スクリプトでこれを設定できます(Sudo
powers required):
#!/bin/bash
### Inputs ###
swap_GB=$(expr 1) # Enter here size of the swap memory to create, in GB.
swap_bs=$(expr 4096) # Enter here block size, in bytes (must be a multiple of 8).
HDD_folder="/media/myhdd/" # Enter absolute path of HDD inside the brackets.
### Swap creation ###
swap_size=$(expr $swap_GB \* 1024 \* 1024 \* 1024 / $swap_bs)
dd if=/dev/zero of=${HDD_folder}"/swapfile" bs=$swap_bs count=$swap_size
mkswap ${HDD_folder}"/swapfile" -f
swapon -p 1000 ${HDD_folder}"/swapfile"
### EOF ###
PS:可能であれば最適化/修正してください。言ったように、それは私の最初のスクリプトです:)
HDD/SSDにスワップ部分がある場合は、zswap
を使用します。 Thoモジュールzram
はHDD/SSDにスワップ部分がないため、Hakalaの答えは適用されません。説明については、スレッド zram vs zswap vs zcache Ultimateガイド:どちらを使用するか を参照してください。スレッドで説明されているようにzswap
を設定します buntu 16.04でMatlabの計算のためにZswapを正常にアクティブにする方法?
/etc/default/grub
の対応する行を次の行に置き換えます
# https://wiki.archlinux.org/index.php/Zswap
GRUB_CMDLINE_LINUX_DEFAULT="quiet splash zswap.enabled=1 zswap.max_pool_percent=25 zswap.compressor=lzo"
Sudo update-grub
を実行します。