20190527のLinuxに関する記事は6件です。

Lenovo Yoga Pro3 に Lubuntu をインストール

はじめに

シンプルなITライフを目指して、シンプルなOSの Lubuntu を使うことにしました。
とりあえず手元にあるあまりつかっていない Lenovo Yoga Pro3 にインストールします。
Lubuntu は ubuntu の軽量版で、 LXQtベースのディストリビューションです。
今回インストールする Lubuntu は 19.04 の最新版です。

この記事を読むとできるようになること。

  • Broadcom ベースの無線LANボードから無線LAN (EAP-TLS) に接続できるようになります。
  • Lubuntu で親指シフトを使った日本語入力ができるようになります。
  • Fortigateの証明書をインポートできます。

Lubuntuのダウンロードからインストールまで

ここは簡単なので適当に。

  1. lubuntuの公式サイトからisoファイルをダウンロード
    0001.JPG

  2. インストールしたisoファイルをブート可能なメディアを作成。

  3. メディアからブートして、Install Lubuntuを実行。

無線LAN に接続できない

どうもこの Lenovo Yoga Pro3に積まれている Broadcom BCM4352 という無線LANボードとは相性が悪いようで接続できないという書き込みをよく見かけます。
そのため次の手順で設定していきます。

1- Secure Boot を Off にする。
一旦電源を切った状態で、電源ボタン近くの小さいボタンをボールペン等で押します。そうすると、電源が入り、ブートメニューが表示されます。ここで、BIOSの設定から Secure Boot を Off にします。

2- 次にいったん有線LANで接続し(USBの有線LANアダプターを使用)、apt を更新します。

sudo apt-get update && sudo apt-get upgrade

3- 次にドライバーをインストールします。(いろいろやっていて入ってしまったのか、もともと入っていたのかは分かりませんが、先に別のドライバーもアンインストールしておきます。)

sudo apt-get purge bcmwl-kernel-source
sudo apt-get install broadcom-sta-dkms

4- 再起動

reboot

5- これで wlpls0という無線アダプターがでてくるので、 NetworkManager から SSIDの設定をします。

これで通常の無線LANには接続できるようにはなりましたが、ステルスモードのSSIDには接続できません。
この辺りはまだ調査中です。

EAP-TLSで無線に接続

どうもいまのバージョンでは無線設定は netplan を使った設定に変わったようで、
scan_ssid=1 というオプションが使えなくなったため、ステルス SSID には接続できなくなっています。
というわけでステルスでない前提で設定方法を書いておきます。
ここで使用する証明書と秘密鍵は事前に入手しておきます。

/etc/netplan/01-network-manager-all.yaml
# Let NetworkManager manage all devices on this system
network:
  wifis:
          wlp1s0:
                  dhcp4: true
                  access-points:

                          "SSID NAME":
                                  auth:
                                          key-management: eap
                                          method: tls
                                          identity: PCHOGEHOGE
                                          ca-certificate: "/home/hogehoge/Documents/hogehoge.pem"
                                          client-certificate: "/home/hogehoge/Documents/hogehoge.pem"
                                          client-key: "/home/hogehoge/Documents/PCHOGEHOGE_02FF.p12"
                                          client-key-password: "password"

  version: 2
  renderer: NetworkManager

設定できたら次のコマンドで確認してみます。

sudo netplan --debug generate

特に問題なければ次のコマンドで適用します。

sudo netplan apply

日本語入力の設定

sudo apt install language-pack-ja fonts-noto-cjk-extra fonts-noto-color-emoji fonts-noto fcitx-mozc
reboot

日本語入力には Google日本語入力 のオープンソース版 mozc と、フォントセット noto を使用します。
再起動すると日本語入力ができるようになっています。

ディレクトリ名は英語にしておく

LANG=C xdg-user-dirs-update --force

参考URL

Lubuntu 18.10 その11 - 日本語を入力できるようにするには・日本語向けパッケージのインストール
KDEのhomeディレクトリを英語にする

Google Chrome

デフォルトで Firefox が入っていますが、 Google Chrome をインストールします。
こちらは Google から deb ファイルをダウンロードしてインストールします。

親指シフトの設定

oyainputというソフトを使って親指シフトを使えるようにします。
git、gcc、makeが必要なようですが、この時点ではどれも最新のものが入っていますので、そのまま oyainput のインストールにすすみます。

oyainput のインストール

cd
mkdir work
cd work
git clone https://github.com/inwskatsube/oyainput.git
cd oyainput
make
sudo make install

これでインストールできたわけですが、起動時にキーボードを複数認識するようになり、選択する必要があります。

IM auto-detect: fcitx
Load config: /home/hogehoge/.oyainputconf
LOYAKEY: SPACE
ROYAKEY: HENKAN
multiple keyboard is detected.
0: AT Translated Set 2 keyboard
1: Microsoft Microsoft Nano Transceiver 1.1
2: Microsoft Microsoft Nano Transceiver 1.1
Enter keyboard number: 0

ここでは 0 を選択し [Enter] を押します。

親指シフトがきちんと動作することを確認できたらデフォルトで選択されるキーボードを設定します。

~/.oyainputconf を開き先頭にある KEYBOARDNAME のところを変更します。

# キーボード名
#KEYBOARDNAME=XXXX
KEYBOARDNAME=AT Translated Set 2 keyboard

fcitx側で日本語入力の ON/OFF 切り替えのキーを設定しました。

0002.png

入力メソッドのオンオフを [ctrl]+[Space] から [変換] に変えました。
もう一つは [無変換] にしました。]]]

最後に oyainputの自動起動設定をします。
[LxQtセッションの設定] に次の内容を追加して自動起動の設定をします。

0001.png

参考URL

Linuxで親指シフトを利用する(Mozcとlibkkcの場合)

TouchPad のスクロール方向を変える

TouchPadのスクロールの方向が上下反対でどうも操作がしにくいので、反転させます。

0003.png

キーボードとマウスの設定から、 [Mouse and Touchpad] を選択。
Device は "Synaptics TM2714-001" を選択します。
その中の Natural Scrolling にチェックを入れると上下反転します。

Fortigateの証明書をインストール

Fortigateのプロキシ配下で使用し、 Deep Inspection が設定されているため、証明書をインストールしてやります。

証明書をインストールするには、システム側と Chrome側と二通り必要です。

システム側への証明書インストール

sudo cp Fortinet_CA_SSL.cer /usr/share/ca-certificates
sudo vi /etc/ca-certificates.conf
ca-certificates.conf
(省略)

mozilla/ePKI_Root_Certification_Authority.crt
mozilla/thawte_Primary_Root_CA.crt
mozilla/thawte_Primary_Root_CA_-_G2.crt
mozilla/thawte_Primary_Root_CA_-_G3.crt
Fortinet_CA_SSL.cer

最後に Fortinet_CA_SSL.cer を追加します。

sudo update-ca-certificates

ブラウザ用証明書インストール

sudo apt-get install libnss3-tools

次に次のようなスクリプトを作成します。

addcert
#!/bin/bash

### Script installs root.cert.pem to certificate trust store of applications using NSS
### (e.g. Firefox, Thunderbird, Chromium)
### Mozilla uses cert8, Chromium and Chrome use cert9

###
### Requirement: apt install libnss3-tools
###


###
### CA file to install (CUSTOMIZE!)
###

certfile="Fortinet_CA_SSL.cer"
certname="Fortinet"


###
### For cert8 (legacy - DBM)
###

for certDB in $(find ~/ -name "cert8.db")
do
    certdir=$(dirname ${certDB});
    certutil -A -n "${certname}" -t "TCu,Cu,Tu" -i ${certfile} -d dbm:${certdir}
done


###
### For cert9 (SQL)
###

for certDB in $(find ~/ -name "cert9.db")
do
    certdir=$(dirname ${certDB});
    certutil -A -n "${certna

次にこのスクリプトを実行します。

bash addcert

参考URL

How to import CA root certificates on Linux and Windows

リモートデスクトップクライアントのインストール

仕事では何かと Windows を使う必要がでてきますので、リモートデスクトップ暗いアンドをインストールしておきます。

sudo apt-get install remmina

リモート先との親指シフトの調整はまた別途

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

ddに頼らずにLinuxのブートディスクを交換する方法(LVMでもない)

どんな話?

  • 一度構築したLinux環境を、別のディスクに移行したい
    • HDD→SSD
    • 小さいSSD→大きいSSD
    • 他にもいろいろあるよね
  • でもLVM組んでない
  • というか /boot とか /boot/efi とかどうすんの
    • 特に /boot/efi はLVM組んでても避けられない
  • 調べるとddを使う方法が出てくるけど…
    • ディスクのサイズが違う
    • GPartedとかで頑張ったけど失敗した

…という状況のときに、ddじゃなくてファイルコピーして頑張ろうという話。
この記事はFedora 30で実践して書いたけど、他のディストリビューションでも通用する…はず。
(Fedoraなら普通はLVMになるけど説明用です(´・ω・`) )

あとパーティションテーブルがGPTなのが前提。MBRだとパーティション操作が変わってしまうし、大抵BIOSブートなのでgrub2-installなどが必要になる。

概要

gdisk と mkfs と mount と rsync と /etc/fstab でがんばる。

手順

root権限が必要なコマンドは sudo をつけてある。
sudoを使わない環境では適宜読み替えること。

古いブートディスクの確認

古いブートディスクを探す

まず古いブートディスクはどこにいるのか確認する。
とりあえずdfコマンドを使う。

$ df
ファイルシス            1K-ブロック       使用     使用可 使用% マウント位置
# ブートディスク以外は省略
/dev/sda1                    102182       7958      94224    8% /boot/efi
/dev/sda2                    491604     195493     266415   43% /boot
/dev/sda3                 136856160   13441568  116393024   11% /

環境によっては /boot や /boot/efi がないやつもある。
とりあえず、これでブートディスクが /dev/sda だとわかる。
(他の名前だった場合は以下の /dev/sda をそいつに読み替えること。)
ここで /dev/mapper/**** とか出てたら、そのパーティションはLVMだ。
その場合はLVMパーティションを作るのはいいが、実際のデータ移動はpvmoveで行うことになる。

古いブートディスクのパーティションテーブルを確認する

次はブートディスクのパーティションテーブルを確認する。
gdiskを使う。もし「コマンドが見つかりません」とか出たらaptなりdnfなりでインストールする。

$ sudo gdisk /dev/sda
GPT fdisk (gdisk) version 1.0.4

Partition table scan:
  MBR: protective
  BSD: not present
  APM: not present
  GPT: present

Found valid GPT with protective MBR; using GPT.

「ちゃんとGPTパーティションがあるよ」と教えてくれている。
もし違う表示が出たら要注意。このまま続行しても失敗する可能性がある。

そしてパーティション一覧を出すには"p"という1文字のコマンドを打つ。
ヘルプは"?"で出る。

Command (? for help): p
Disk /dev/sda: 312581808 sectors, 149.0 GiB
Model: INTEL SSDSC2BB16
Sector size (logical/physical): 512/4096 bytes
Disk identifier (GUID): 7F41B9E9-BAE1-4F38-8C13-2CD6725320C3
Partition table holds up to 128 entries
Main partition table begins at sector 2 and ends at sector 33
First usable sector is 34, last usable sector is 312581774
Partitions will be aligned on 2-sector boundaries
Total free space is 1679 sectors (839.5 KiB)

Number  Start (sector)    End (sector)  Size       Code  Name
   1            2048          206847   100.0 MiB   EF00  EFI System Partition
   2          206848         1230847   500.0 MiB   8300  Linux filesystem
   3         1230848       312580095   148.5 GiB   8300  Linux filesystem

ここで必要なのは、最後に出ているパーティション一覧である。
これを丸ごとメモしておこう。
大抵のSSHクライアントならドラッグ等で選択からのコピペが効く。
実機を直接叩いてたりするなら携帯のカメラでも構わない。

新しいディスクの準備

新しいディスクを探す

まずは新しいディスクを探す必要がある。

$ sudo ls /dev/sd*
/dev/sda /dev/sda1 /dev/sda2 /dev/sda3 /dev/sdb

/dev/sdb にはパーティションが一つもないことがわかる。
というわけで"多分"これが新しいディスクである。
こんなディスクが複数ある場合は、事故防止のためにも、PCの電源を切ってから、古いブートディスクと新しいブートディスク以外を外して出直すのがよい。ただし、/etc/fstab で別のディスクをマウントしている場合は適宜コメントアウトで無効化などを行うこと。
もっとも、他のPCなどで使ったディスク等を使いまわす場合はこの方法では探せない(すでにパーティションがある!)ので総当たりが必要。

gdiskで本当にこれが新しいブートディスク(にしたいディスク)かどうか確認する。

$ sudo gdisk /dev/sdb
GPT fdisk (gdisk) version 1.0.4

Partition table scan:
  MBR: not present
  BSD: not present
  APM: not present
  GPT: not present

Creating new GPT entries in memory.

「パーティションテーブルがないよ」と教えてくれている。
パーティションテーブルを作る前に、まずは本当に目当ての新しいブートディスクかどうか確認する。

Command (? for help): p
Disk /dev/sdb: 3125627568 sectors, 1.5 TiB
Model: VK1600GECVP
Sector size (logical/physical): 512/4096 bytes
Disk identifier (GUID): 4C86D095-3737-4895-93CC-DFB9196FFB46
Partition table holds up to 128 entries
Main partition table begins at sector 2 and ends at sector 33
First usable sector is 34, last usable sector is 3125627534
Partitions will be aligned on 2048-sector boundaries
Total free space is 3125627501 sectors (1.5 TiB)

Number  Start (sector)    End (sector)  Size       Code  Name

Model(ディスクの型番)やディスク容量などを見て確認する。
逆に言えばこれくらいしか手掛かりがないので、事故防止のためにもブートディスク交換と関係ないディスクは外しておくことを勧める。

パーティションテーブルを作成する

これだ、と確認したらパーティションを作っていく。
先にメモしたパーティション一覧を使う。
すでにパーティションがある場合は"d"コマンドで消してから行う。

パーティション1個を作る操作はこのようになる。

Command (? for help): n
Partition number (1-128, default 1): #何も入れずにEnter
First sector (34-3125627534, default = 2048) or {+-}size{KMGTP}: #何も入れずにEnter
Last sector (34-3125627534, default = 3125627534) or {+-}size{KMGTP}: +100M
Current type is 'Linux filesystem'
Hex code or GUID (L to show codes, Enter = 8300): EF00
Changed type of partition to 'EFI System'
  • "Last sector"の行でパーティションの大きさを決められる
    • "+100M" と入れると100MBのパーティションになる
    • "+100G" なども使える
    • /boot と /boot/efi については古いブートディスクに合わせるとよい
    • 何も入れずにEnterを押すとディスクの終わりまで全部使う。"/"(ルートパーティション)は最後にこれで作るとよい
  • "Hex code or GUID"の行でパーティションの種類を指定する
    • これは必ず古いブートディスクの各パーティションの"Code"と同じにする

基本的には古いブートディスクと同じ順番でパーティションを作っていく。順番を変えると事故の元なのでおすすめしない。
全部入れるとこのようになる。
この例では /boot/efi と /boot 用のパーティションは古いブートディスクのものと同じ大きさとし、残り全部を /(ルートパーティション) に割り当てた。

Command (? for help): p

# ディスク情報は省略

Number  Start (sector)    End (sector)  Size       Code  Name
   1            2048          206847   100.0 MiB   EF00  EFI System Partition
   2          206848         1230847   500.0 MiB   8300  Linux filesystem
   3         1230848      3125627534   1.5 TiB     8300  Linux filesystem

最後に"w"コマンドでパーティションテーブルを書き込む。
これは取り消せないのでよく確認すること。
逆に言えばこれをやる前ならやり直しが効く。("q" コマンドでgdiskを終了など)

Command (? for help): w

Final checks complete. About to write GPT data. THIS WILL OVERWRITE EXISTING PARTITIONS!!

Do you want to proceed? (Y/N): y
OK; writing new GUID partition table (GPT) to /dev/sdb.
The operation has completed successfully.

新しいブートディスクをフォーマットする

まず、新しく作ったパーティションをLinuxが認識しているかどうか確認する。

$ sudo ls /dev/sd*
/dev/sda /dev/sda1 /dev/sda2 /dev/sda3 /dev/sdb /dev/sdb1 /dev/sdb2 /dev/sdb3

この例では /dev/sdb[1-3] が増えているのでOKだ。
もし増えていない場合は再起動が必要だが、以下の注意が必要。

  • 空のEFIシステムパーティションを作ってしまったのでブートに失敗する可能性がある
    • ブートデバイスを手動で選択すればブートできるはず
  • 再起動後に /dev/sd[abc…] が入れ替わっている可能性がある
    • 必ず「古いブートデバイスを探す」をやり直してよく確認すること!

無事に出来たらフォーマットをしていく。
dfコマンドで古いブートディスクの各パーティションのファイルシステムを確認する。

$ df -T
ファイルシス            タイプ   1K-ブロック       使用     使用可 使用% マウント位置
# ブートディスク以外は省略
/dev/sda1               vfat          102182       7958      94224    8% /boot/efi
/dev/sda2               ext4          491604     195493     266415   43% /boot
/dev/sda3               ext4       136856160   13442692  116391900   11% /

この「タイプ」に合わせて、新しいブートディスクの各パーティションをフォーマットしていく。
基本的には"mkfs.***" に「タイプ」を当てはめればそのファイルシステムでフォーマットできる。

$ mkfs.vfat /dev/sdb1
# 出力は省略
$ mkfs.ext4 /dev/sdb2
# 出力は省略
$ mkfs.ext4 /dev/sdb3
# 出力は省略

いよいよファイルコピー

これからのの作業は、使用しているLinuxディストリビューションのインストールディスクなりLive USBメモリなりを用意して、そこからブートして行う必要がある。

新旧ブートディスクを探す

まずはディスクの一覧を見る。

$ sudo ls /dev/sd*
/dev/sda /dev/sda1 /dev/sda2 /dev/sda3 /dev/sdb /dev/sdb1 /dev/sdb2 /dev/sdb3
/dev/sdc /dev/sdc1

そして /dev/sd[abc…] それぞれをgdiskで表示して新旧ブートディスクを特定する。

$ sudo gdisk /dev/sda
GPT fdisk (gdisk) version 1.0.4

Partition table scan:
  MBR: protective
  BSD: not present
  APM: not present
  GPT: present

Found valid GPT with protective MBR; using GPT.
Command (? for help): p
Disk /dev/sda: 312581808 sectors, 149.0 GiB
Model: INTEL SSDSC2BB16
Sector size (logical/physical): 512/4096 bytes
Disk identifier (GUID): 7F41B9E9-BAE1-4F38-8C13-2CD6725320C3
Partition table holds up to 128 entries
Main partition table begins at sector 2 and ends at sector 33
First usable sector is 34, last usable sector is 312581774
Partitions will be aligned on 2-sector boundaries
Total free space is 1679 sectors (839.5 KiB)

Number  Start (sector)    End (sector)  Size       Code  Name
   1            2048          206847   100.0 MiB   EF00  EFI System Partition
   2          206848         1230847   500.0 MiB   8300  Linux filesystem
   3         1230848       312580095   148.5 GiB   8300  Linux filesystem

この例では /dev/sda が古いブートディスクだ。
同様に残りの /dev/sd[bc…] も確認する。

以下は

  • 古いブートディスク: /dev/sda
  • 新しいブートディスク : /dev/sdb

だったとして記載する。前の作業とは名前が変わっていることも多いので要注意。

各パーティションをマウントしてコピーする

特定した各パーティションをマウントしてコピーする

# 手動マウントはどこでもできるけど /mnt にフォルダを作るのがお約束
$ sudo cd /mnt

# 古いブートディスクの /boot/efi をマウント
# フォルダ名はなんでもいいけど事故防止のためわかりやすくしよう
$ sudo mkdir efi_old
$ sudo mount /dev/sda1 efi_old

# 新しいブートディスクの /boot/efi をマウント
$ sudo mkdir efi_new
$ sudo mount /dev/sdb1 efi_new

# コピーするよ!
# efi_old の「中身を」efi_newにコピー
$ sudo rsync -aHAXxSvP efi_old/ efi_new/

rsyncのオプションはググれば出てくるが、概ね「ファイルシステムをそっくりそのままコピーし(aHAXxS)、進捗を表示する(vP)」という意味。
オプションの文字の順番は問われないが、大小文字は区別されるので間違えないように。
また"efi_old/"の最後の"/"を付け忘れると、efi_new の中に efi_old というフォルダが作られてその中にコピーされてしまうので必ずつける必要がある。

残りのパーティションも同様にコピーする。

# /boot をコピー
$ sudo mkdir boot_old
$ sudo mount /dev/sda2 boot_old
$ sudo mkdir boot_new
$ sudo mount /dev/sdb2 boot_new
$ sudo rsync -aHAXxSvP boot_old/ boot_new/

# / (ルートパーティション)をコピー
$ sudo mkdir root_old
$ sudo mount /dev/sda3 root_old
$ sudo mkdir root_new
$ sudo mount /dev/sdb3 root_new
$ sudo rsync -aHAXxSvP root_old/ root_new/

「新しいブートディスクの」/etc/fstab を編集する

ddでディスクコピーをした場合とは異なり、/etc/fstabを編集しないとブートに失敗する。
「新しいブートディスクの」 /etc/fstab を編集する必要がある。

その前に各パーティションのUUIDをメモしておく。blkidコマンドを使う。

$ sudo blkid
# 新しいブートディスク以外は省略
/dev/sdb1: SEC_TYPE="msdos" UUID="2FED-0CE8" TYPE="vfat" PARTLABEL="EFI System Partition" PARTUUID="24dfff22-b893-469d-a94c-dde0d53522bc"
/dev/sdb2: UUID="c1b31131-99e7-41ee-86e2-a2e3e5b46033" TYPE="ext4" PARTLABEL="Linux Filesystem" PARTUUID="7aaf4b56-9de3-464e-87f6-f13a2c0b7eb7"
/dev/sdb3: UUID="7d255831-7a7e-4c39-9c27-a51190b4b12e" TYPE="ext4" PARTLABEL="Linux Filesystem" PARTUUID="b04a09cf-e64e-4385-b74c-d8b4231611f1"

先の例では /mnt/root_new に新しいブートディスクのルートパーティションをマウントしたので
/mnt/root_new/etc/fstab を編集すればいい。

# お好みのテキストエディタで /mnt/root_new/etc/fstab を開く
# nanoとかviとか 例ではviだけど
$ vi /mnt/root_new/etc/fstab

各行は先頭から file system(マウントするパーティション), mount point, type…と並んでいる(詳しくはググって)。
ここでは先頭の"file system"だけ書き換えればよい。
この部分を、blkidコマンドの"UUID"の値に書き換える。
"PARTUUID"でも動くが、どういうわけかLinuxインストーラーはUUIDを使いたがるので倣っておく。
書き換えが終わるとこんな感じになる。

/etc/fstab
# ブートディスク以外は省略
UUID="7d255831-7a7e-4c39-9c27-a51190b4b12e" /                       ext4    defaults        1 1
UUID="c1b31131-99e7-41ee-86e2-a2e3e5b46033" /boot                   ext4    defaults        1 2
UUID="2FED-0CE8"                            /boot/efi               vfat    umask=0077,shortname=winnt 0 2

行の順番を入れ替えたくなるかもしれないがやめておこう。

新しいブートディスクで起動

PCの電源を切ってから、古いブートディスクやコピー時の起動に使ったUSBメモリを外す。
その後電源を入れて、無事に新しいブートディスクから起動したら完了だ。
/etc/fstabで他のディスクをマウントするようにしてあった場合は再び有効にしよう。

起動に失敗した場合は、再びLive USBメモリ等から起動して、新しいブートディスクの中身を確認しよう。
(gdiskでパーティションテーブルを確認したり、各パーティションを mount して中身を確認したりする。)

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

ddに頼らずにLinuxのブートディスクをコピーする方法(LVMでもない)

どんな話?

  • 一度構築したLinux環境を、別のディスクに移行したい
    • HDD→SSD
    • 小さいSSD→大きいSSD
    • 他にもいろいろあるよね
  • でもLVM組んでない
  • というか /boot とか /boot/efi とかどうすんの
    • 特に /boot/efi はLVM組んでても避けられない
  • 調べるとddを使う方法が出てくるけど…
    • ディスクのサイズが違う
    • GPartedとかで頑張ったけど失敗した

…という状況のときに、ddじゃなくてファイルコピーして頑張ろうという話。
この記事はFedora 30で実践して書いたけど、他のディストリビューションでも通用する…はず。
(Fedoraなら普通はLVMになるけど説明用です(´・ω・`) )

あとパーティションテーブルがGPTなのが前提。MBRだとパーティション操作が変わってしまうし、大抵BIOSブートなのでgrub2-installなどが必要になる。

概要

gdisk と mkfs と mount と rsync と /etc/fstab でがんばる。

手順

root権限が必要なコマンドは sudo をつけてある。
sudoを使わない環境では適宜読み替えること。

古いブートディスクの確認

古いブートディスクを探す

まず古いブートディスクはどこにいるのか確認する。
とりあえずdfコマンドを使う。

$ df
ファイルシス            1K-ブロック       使用     使用可 使用% マウント位置
# ブートディスク以外は省略
/dev/sda1                    102182       7958      94224    8% /boot/efi
/dev/sda2                    491604     195493     266415   43% /boot
/dev/sda3                 136856160   13441568  116393024   11% /

環境によっては /boot や /boot/efi がないやつもある。
とりあえず、これでブートディスクが /dev/sda だとわかる。
(他の名前だった場合は以下の /dev/sda をそいつに読み替えること。)
ここで /dev/mapper/**** とか出てたら、そのパーティションはLVMだ。
その場合はLVMパーティションを作るのはいいが、実際のデータ移動はpvmoveで行うことになる。

古いブートディスクのパーティションテーブルを確認する

次はブートディスクのパーティションテーブルを確認する。
gdiskを使う。もし「コマンドが見つかりません」とか出たらaptなりdnfなりでインストールする。

$ sudo gdisk /dev/sda
GPT fdisk (gdisk) version 1.0.4

Partition table scan:
  MBR: protective
  BSD: not present
  APM: not present
  GPT: present

Found valid GPT with protective MBR; using GPT.

「ちゃんとGPTパーティションがあるよ」と教えてくれている。
もし違う表示が出たら要注意。このまま続行しても失敗する可能性がある。

そしてパーティション一覧を出すには"p"という1文字のコマンドを打つ。
ヘルプは"?"で出る。

Command (? for help): p
Disk /dev/sda: 312581808 sectors, 149.0 GiB
Model: INTEL SSDSC2BB16
Sector size (logical/physical): 512/4096 bytes
Disk identifier (GUID): 7F41B9E9-BAE1-4F38-8C13-2CD6725320C3
Partition table holds up to 128 entries
Main partition table begins at sector 2 and ends at sector 33
First usable sector is 34, last usable sector is 312581774
Partitions will be aligned on 2-sector boundaries
Total free space is 1679 sectors (839.5 KiB)

Number  Start (sector)    End (sector)  Size       Code  Name
   1            2048          206847   100.0 MiB   EF00  EFI System Partition
   2          206848         1230847   500.0 MiB   8300  Linux filesystem
   3         1230848       312580095   148.5 GiB   8300  Linux filesystem

ここで必要なのは、最後に出ているパーティション一覧である。
これを丸ごとメモしておこう。
大抵のSSHクライアントならドラッグ等で選択からのコピペが効く。
実機を直接叩いてたりするなら携帯のカメラでも構わない。

新しいディスクの準備

新しいディスクを探す

まずは新しいディスクを探す必要がある。

$ sudo ls /dev/sd*
/dev/sda /dev/sda1 /dev/sda2 /dev/sda3 /dev/sdb

/dev/sdb にはパーティションが一つもないことがわかる。
というわけで"多分"これが新しいディスクである。
こんなディスクが複数ある場合は、事故防止のためにも、PCの電源を切ってから、古いブートディスクと新しいブートディスク以外を外して出直すのがよい。ただし、/etc/fstab で別のディスクをマウントしている場合は適宜コメントアウトで無効化などを行うこと。
もっとも、他のPCなどで使ったディスク等を使いまわす場合はこの方法では探せない(すでにパーティションがある!)ので総当たりが必要。

gdiskで本当にこれが新しいブートディスク(にしたいディスク)かどうか確認する。

$ sudo gdisk /dev/sdb
GPT fdisk (gdisk) version 1.0.4

Partition table scan:
  MBR: not present
  BSD: not present
  APM: not present
  GPT: not present

Creating new GPT entries in memory.

「パーティションテーブルがないよ」と教えてくれている。
パーティションテーブルを作る前に、まずは本当に目当ての新しいブートディスクかどうか確認する。

Command (? for help): p
Disk /dev/sdb: 3125627568 sectors, 1.5 TiB
Model: VK1600GECVP
Sector size (logical/physical): 512/4096 bytes
Disk identifier (GUID): 4C86D095-3737-4895-93CC-DFB9196FFB46
Partition table holds up to 128 entries
Main partition table begins at sector 2 and ends at sector 33
First usable sector is 34, last usable sector is 3125627534
Partitions will be aligned on 2048-sector boundaries
Total free space is 3125627501 sectors (1.5 TiB)

Number  Start (sector)    End (sector)  Size       Code  Name

Model(ディスクの型番)やディスク容量などを見て確認する。
逆に言えばこれくらいしか手掛かりがないので、事故防止のためにもブートディスク交換と関係ないディスクは外しておくことを勧める。

パーティションテーブルを作成する

これだ、と確認したらパーティションを作っていく。
先にメモしたパーティション一覧を使う。
すでにパーティションがある場合は"d"コマンドで消してから行う。

パーティション1個を作る操作はこのようになる。

Command (? for help): n
Partition number (1-128, default 1): #何も入れずにEnter
First sector (34-3125627534, default = 2048) or {+-}size{KMGTP}: #何も入れずにEnter
Last sector (34-3125627534, default = 3125627534) or {+-}size{KMGTP}: +100M
Current type is 'Linux filesystem'
Hex code or GUID (L to show codes, Enter = 8300): EF00
Changed type of partition to 'EFI System'
  • "Last sector"の行でパーティションの大きさを決められる
    • "+100M" と入れると100MBのパーティションになる
    • "+100G" なども使える
    • /boot と /boot/efi については古いブートディスクに合わせるとよい
    • 何も入れずにEnterを押すとディスクの終わりまで全部使う。"/"(ルートパーティション)は最後にこれで作るとよい
  • "Hex code or GUID"の行でパーティションの種類を指定する
    • これは必ず古いブートディスクの各パーティションの"Code"と同じにする

基本的には古いブートディスクと同じ順番でパーティションを作っていく。順番を変えると事故の元なのでおすすめしない。
全部入れるとこのようになる。
この例では /boot/efi と /boot 用のパーティションは古いブートディスクのものと同じ大きさとし、残り全部を /(ルートパーティション) に割り当てた。

Command (? for help): p

# ディスク情報は省略

Number  Start (sector)    End (sector)  Size       Code  Name
   1            2048          206847   100.0 MiB   EF00  EFI System Partition
   2          206848         1230847   500.0 MiB   8300  Linux filesystem
   3         1230848      3125627534   1.5 TiB     8300  Linux filesystem

最後に"w"コマンドでパーティションテーブルを書き込む。
これは取り消せないのでよく確認すること。
逆に言えばこれをやる前ならやり直しが効く。("q" コマンドでgdiskを終了など)

Command (? for help): w

Final checks complete. About to write GPT data. THIS WILL OVERWRITE EXISTING PARTITIONS!!

Do you want to proceed? (Y/N): y
OK; writing new GUID partition table (GPT) to /dev/sdb.
The operation has completed successfully.

新しいブートディスクをフォーマットする

まず、新しく作ったパーティションをLinuxが認識しているかどうか確認する。

$ sudo ls /dev/sd*
/dev/sda /dev/sda1 /dev/sda2 /dev/sda3 /dev/sdb /dev/sdb1 /dev/sdb2 /dev/sdb3

この例では /dev/sdb[1-3] が増えているのでOKだ。
もし増えていない場合は再起動が必要だが、以下の注意が必要。

  • 空のEFIシステムパーティションを作ってしまったのでブートに失敗する可能性がある
    • ブートデバイスを手動で選択すればブートできるはず
  • 再起動後に /dev/sd[abc…] が入れ替わっている可能性がある
    • 必ず「古いブートデバイスを探す」をやり直してよく確認すること!

無事に出来たらフォーマットをしていく。
dfコマンドで古いブートディスクの各パーティションのファイルシステムを確認する。

$ df -T
ファイルシス            タイプ   1K-ブロック       使用     使用可 使用% マウント位置
# ブートディスク以外は省略
/dev/sda1               vfat          102182       7958      94224    8% /boot/efi
/dev/sda2               ext4          491604     195493     266415   43% /boot
/dev/sda3               ext4       136856160   13442692  116391900   11% /

この「タイプ」に合わせて、新しいブートディスクの各パーティションをフォーマットしていく。
基本的には"mkfs.***" に「タイプ」を当てはめればそのファイルシステムでフォーマットできる。

$ mkfs.vfat /dev/sdb1
# 出力は省略
$ mkfs.ext4 /dev/sdb2
# 出力は省略
$ mkfs.ext4 /dev/sdb3
# 出力は省略

いよいよファイルコピー

これからのの作業は、使用しているLinuxディストリビューションのインストールディスクなりLive USBメモリなりを用意して、そこからブートして行う必要がある。

新旧ブートディスクを探す

まずはディスクの一覧を見る。

$ sudo ls /dev/sd*
/dev/sda /dev/sda1 /dev/sda2 /dev/sda3 /dev/sdb /dev/sdb1 /dev/sdb2 /dev/sdb3
/dev/sdc /dev/sdc1

そして /dev/sd[abc…] それぞれをgdiskで表示して新旧ブートディスクを特定する。

$ sudo gdisk /dev/sda
GPT fdisk (gdisk) version 1.0.4

Partition table scan:
  MBR: protective
  BSD: not present
  APM: not present
  GPT: present

Found valid GPT with protective MBR; using GPT.
Command (? for help): p
Disk /dev/sda: 312581808 sectors, 149.0 GiB
Model: INTEL SSDSC2BB16
Sector size (logical/physical): 512/4096 bytes
Disk identifier (GUID): 7F41B9E9-BAE1-4F38-8C13-2CD6725320C3
Partition table holds up to 128 entries
Main partition table begins at sector 2 and ends at sector 33
First usable sector is 34, last usable sector is 312581774
Partitions will be aligned on 2-sector boundaries
Total free space is 1679 sectors (839.5 KiB)

Number  Start (sector)    End (sector)  Size       Code  Name
   1            2048          206847   100.0 MiB   EF00  EFI System Partition
   2          206848         1230847   500.0 MiB   8300  Linux filesystem
   3         1230848       312580095   148.5 GiB   8300  Linux filesystem

この例では /dev/sda が古いブートディスクだ。
同様に残りの /dev/sd[bc…] も確認する。

以下は

  • 古いブートディスク: /dev/sda
  • 新しいブートディスク : /dev/sdb

だったとして記載する。前の作業とは名前が変わっていることも多いので要注意。

各パーティションをマウントしてコピーする

特定した各パーティションをマウントしてコピーする

# 手動マウントはどこでもできるけど /mnt にフォルダを作るのがお約束
$ sudo cd /mnt

# 古いブートディスクの /boot/efi をマウント
# フォルダ名はなんでもいいけど事故防止のためわかりやすくしよう
$ sudo mkdir efi_old
$ sudo mount /dev/sda1 efi_old

# 新しいブートディスクの /boot/efi をマウント
$ sudo mkdir efi_new
$ sudo mount /dev/sdb1 efi_new

# コピーするよ!
# efi_old の「中身を」efi_newにコピー
$ sudo rsync -aHAXxSvP efi_old/ efi_new/

rsyncのオプションはググれば出てくるが、概ね「ファイルシステムをそっくりそのままコピーし(aHAXxS)、進捗を表示する(vP)」という意味。
オプションの文字の順番は問われないが、大小文字は区別されるので間違えないように。
また"efi_old/"の最後の"/"を付け忘れると、efi_new の中に efi_old というフォルダが作られてその中にコピーされてしまうので必ずつける必要がある。

残りのパーティションも同様にコピーする。

# /boot をコピー
$ sudo mkdir boot_old
$ sudo mount /dev/sda2 boot_old
$ sudo mkdir boot_new
$ sudo mount /dev/sdb2 boot_new
$ sudo rsync -aHAXxSvP boot_old/ boot_new/

# / (ルートパーティション)をコピー
$ sudo mkdir root_old
$ sudo mount /dev/sda3 root_old
$ sudo mkdir root_new
$ sudo mount /dev/sdb3 root_new
$ sudo rsync -aHAXxSvP root_old/ root_new/

「新しいブートディスクの」/etc/fstab を編集する

ddでディスクコピーをした場合とは異なり、/etc/fstabを編集しないとブートに失敗する。
「新しいブートディスクの」 /etc/fstab を編集する必要がある。

その前に各パーティションのUUIDをメモしておく。blkidコマンドを使う。

$ sudo blkid
# 新しいブートディスク以外は省略
/dev/sdb1: SEC_TYPE="msdos" UUID="2FED-0CE8" TYPE="vfat" PARTLABEL="EFI System Partition" PARTUUID="24dfff22-b893-469d-a94c-dde0d53522bc"
/dev/sdb2: UUID="c1b31131-99e7-41ee-86e2-a2e3e5b46033" TYPE="ext4" PARTLABEL="Linux Filesystem" PARTUUID="7aaf4b56-9de3-464e-87f6-f13a2c0b7eb7"
/dev/sdb3: UUID="7d255831-7a7e-4c39-9c27-a51190b4b12e" TYPE="ext4" PARTLABEL="Linux Filesystem" PARTUUID="b04a09cf-e64e-4385-b74c-d8b4231611f1"

先の例では /mnt/root_new に新しいブートディスクのルートパーティションをマウントしたので
/mnt/root_new/etc/fstab を編集すればいい。

# お好みのテキストエディタで /mnt/root_new/etc/fstab を開く
# nanoとかviとか 例ではviだけど
$ vi /mnt/root_new/etc/fstab

各行は先頭から file system(マウントするパーティション), mount point, type…と並んでいる(詳しくはググって)。
ここでは先頭の"file system"だけ書き換えればよい。
この部分を、blkidコマンドの"UUID"の値に書き換える。
"PARTUUID"でも動くが、どういうわけかLinuxインストーラーはUUIDを使いたがるので倣っておく。
書き換えが終わるとこんな感じになる。

/etc/fstab
# ブートディスク以外は省略
UUID="7d255831-7a7e-4c39-9c27-a51190b4b12e" /                       ext4    defaults        1 1
UUID="c1b31131-99e7-41ee-86e2-a2e3e5b46033" /boot                   ext4    defaults        1 2
UUID="2FED-0CE8"                            /boot/efi               vfat    umask=0077,shortname=winnt 0 2

行の順番を入れ替えたくなるかもしれないがやめておこう。

新しいブートディスクで起動

PCの電源を切ってから、古いブートディスクやコピー時の起動に使ったUSBメモリを外す。
その後電源を入れて、無事に新しいブートディスクから起動したら完了だ。
/etc/fstabで他のディスクをマウントするようにしてあった場合は再び有効にしよう。

起動に失敗した場合は、再びLive USBメモリ等から起動して、新しいブートディスクの中身を確認しよう。
(gdiskでパーティションテーブルを確認したり、各パーティションを mount して中身を確認したりする。)

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

ddに頼らずにLinuxのブートドライブをコピーする方法(LVMでもない)

どんな話?

  • 一度構築したLinux環境を、別のディスクに移行したい
    • HDD→SSD
    • 小さいSSD→大きいSSD
    • 他にもいろいろあるよね
  • でもLVM組んでない
  • というか /boot とか /boot/efi とかどうすんの
    • 特に /boot/efi はLVM組んでても避けられない
  • 調べるとddを使う方法が出てくるけど…
    • ディスクのサイズが違う
    • GPartedとかで頑張ったけど失敗した

…という状況のときに、ddじゃなくてファイルコピーして頑張ろうという話。
この記事はFedora 30で実践して書いたけど、他のディストリビューションでも通用する…はず。
(Fedoraなら普通はLVMになるけど説明用です(´・ω・`) )
…と思ってたらubuntuが想像以上に違っていてめっちゃつらい
ubuntuユーザーはうまいこと読み替えてほしい。

あとパーティションテーブルがGPTなのが前提。MBRだとパーティション操作が変わってしまうし、大抵BIOSブートなのでgrub2-installなどが必要になる。

概要

gdisk と mkfs と mount と rsync と /etc/fstab でがんばる。

手順

root権限が必要なコマンドは sudo をつけてある。
sudoを使わない環境では適宜読み替えること。

古いブートドライブの確認

古いブートドライブを探す

まず古いブートドライブはどこにいるのか確認する。
とりあえずdfコマンドを使う。

$ df
ファイルシス            1K-ブロック       使用     使用可 使用% マウント位置
# ブートドライブ以外は省略
/dev/sda1                    102182       7958      94224    8% /boot/efi
/dev/sda2                    491604     195493     266415   43% /boot
/dev/sda3                 136856160   13441568  116393024   11% /

環境によっては /boot や /boot/efi がないやつもある。
とりあえず、これでブートドライブが /dev/sda だとわかる。
(他の名前だった場合は以下の /dev/sda をそいつに読み替えること。)
ここで /dev/mapper/**** とか出てたら、そのパーティションはLVMだ。
LVMのコピーはこの記事では扱っていないので検索してほしい。その場合でも他のパーティションのコピーはこの記事の方法で可能である。

古いブートドライブのパーティションテーブルを確認する

次はブートドライブのパーティションテーブルを確認する。
gdiskを使う。もし「コマンドが見つかりません」とか出たらaptなりdnfなりでインストールする。

$ sudo gdisk /dev/sda
GPT fdisk (gdisk) version 1.0.4

Partition table scan:
  MBR: protective
  BSD: not present
  APM: not present
  GPT: present

Found valid GPT with protective MBR; using GPT.

「ちゃんとGPTパーティションがあるよ」と教えてくれている。
もし違う表示が出たら要注意。このまま続行しても失敗する可能性がある。

そしてパーティション一覧を出すには"p"という1文字のコマンドを打つ。
ヘルプは"?"で出る。

Command (? for help): p
Disk /dev/sda: 312581808 sectors, 149.0 GiB
Model: INTEL SSDSC2BB16
Sector size (logical/physical): 512/4096 bytes
Disk identifier (GUID): 7F41B9E9-BAE1-4F38-8C13-2CD6725320C3
Partition table holds up to 128 entries
Main partition table begins at sector 2 and ends at sector 33
First usable sector is 34, last usable sector is 312581774
Partitions will be aligned on 2-sector boundaries
Total free space is 1679 sectors (839.5 KiB)

Number  Start (sector)    End (sector)  Size       Code  Name
   1            2048          206847   100.0 MiB   EF00  EFI System Partition
   2          206848         1230847   500.0 MiB   8300  Linux filesystem
   3         1230848       312580095   148.5 GiB   8300  Linux filesystem

ここで必要なのは、最後に出ているパーティション一覧である。
これを丸ごとメモしておこう。
大抵のSSHクライアントならドラッグ等で選択からのコピペが効く。
実機を直接叩いてたりするなら携帯のカメラでも構わない。

なお、この例にはないが、Codeが"EF02"のパーティションがあった場合はコピー時の手順が少し変わる(後述)。
また、Codeが"8E00"のパーティションがある場合は、そいつはLVMの物理ボリュームだ。LVMのコピーはこの記事では扱っていないので検索してほしい。その場合でも他のパーティションのコピーはこの記事の方法で可能である。

新しいディスクの準備

新しいディスクを探す

まずは新しいディスクを探す必要がある。

$ sudo ls /dev/sd*
/dev/sda /dev/sda1 /dev/sda2 /dev/sda3 /dev/sdb

/dev/sdb にはパーティションが一つもないことがわかる。
というわけで"多分"これが新しいディスクである。
こんなディスクが複数ある場合は、事故防止のためにも、PCの電源を切ってから、古いブートドライブと新しいブートドライブ以外を外して出直すのがよい。ただし、/etc/fstab で別のディスクをマウントしている場合は適宜コメントアウトで無効化などを行うこと。
もっとも、他のPCなどで使ったディスク等を使いまわす場合はこの方法では探せない(すでにパーティションがある!)ので総当たりが必要。

gdiskで本当にこれが新しいブートドライブ(にしたいディスク)かどうか確認する。

$ sudo gdisk /dev/sdb
GPT fdisk (gdisk) version 1.0.4

Partition table scan:
  MBR: not present
  BSD: not present
  APM: not present
  GPT: not present

Creating new GPT entries in memory.

「パーティションテーブルがないよ」と教えてくれている。
パーティションテーブルを作る前に、まずは本当に目当ての新しいブートドライブかどうか確認する。

Command (? for help): p
Disk /dev/sdb: 3125627568 sectors, 1.5 TiB
Model: VK1600GECVP
Sector size (logical/physical): 512/4096 bytes
Disk identifier (GUID): 4C86D095-3737-4895-93CC-DFB9196FFB46
Partition table holds up to 128 entries
Main partition table begins at sector 2 and ends at sector 33
First usable sector is 34, last usable sector is 3125627534
Partitions will be aligned on 2048-sector boundaries
Total free space is 3125627501 sectors (1.5 TiB)

Number  Start (sector)    End (sector)  Size       Code  Name

Model(ディスクの型番)やディスク容量などを見て確認する。
逆に言えばこれくらいしか手掛かりがないので、事故防止のためにもブートドライブ交換と関係ないディスクは外しておくことを勧める。

パーティションテーブルを作成する

これだ、と確認したらパーティションを作っていく。
先にメモしたパーティション一覧を使う。
すでにパーティションがある場合は"d"コマンドで消してから行う。

パーティション1個を作る操作はこのようになる。

Command (? for help): n
Partition number (1-128, default 1): #何も入れずにEnter
First sector (34-3125627534, default = 2048) or {+-}size{KMGTP}: #何も入れずにEnter
Last sector (34-3125627534, default = 3125627534) or {+-}size{KMGTP}: +100M
Current type is 'Linux filesystem'
Hex code or GUID (L to show codes, Enter = 8300): EF00
Changed type of partition to 'EFI System'
  • "Last sector"の行でパーティションの大きさを決められる
    • "+100M" と入れると100MBのパーティションになる
    • "+100G" なども使える
    • /boot と /boot/efi については古いブートドライブに合わせるとよい
    • 何も入れずにEnterを押すとディスクの終わりまで全部使う。"/"(ルートパーティション)は最後にこれで作るとよい
  • "Hex code or GUID"の行でパーティションの種類を指定する
    • これは必ず古いブートドライブの各パーティションの"Code"と同じにする

基本的には古いブートドライブと同じ順番でパーティションを作っていく。順番を変えると事故の元なのでおすすめしない。
全部入れるとこのようになる。
この例では /boot/efi と /boot 用のパーティションは古いブートドライブのものと同じ大きさとし、残り全部を /(ルートパーティション) に割り当てた。

Command (? for help): p

# ディスク情報は省略

Number  Start (sector)    End (sector)  Size       Code  Name
   1            2048          206847   100.0 MiB   EF00  EFI System Partition
   2          206848         1230847   500.0 MiB   8300  Linux filesystem
   3         1230848      3125627534   1.5 TiB     8300  Linux filesystem

最後に"w"コマンドでパーティションテーブルを書き込む。
これは取り消せないのでよく確認すること。
逆に言えばこれをやる前ならやり直しが効く。("q" コマンドでgdiskを終了など)

Command (? for help): w

Final checks complete. About to write GPT data. THIS WILL OVERWRITE EXISTING PARTITIONS!!

Do you want to proceed? (Y/N): y
OK; writing new GUID partition table (GPT) to /dev/sdb.
The operation has completed successfully.

新しいブートドライブをフォーマットする

まず、新しく作ったパーティションをLinuxが認識しているかどうか確認する。

$ sudo ls /dev/sd*
/dev/sda /dev/sda1 /dev/sda2 /dev/sda3 /dev/sdb /dev/sdb1 /dev/sdb2 /dev/sdb3

この例では /dev/sdb[1-3] が増えているのでOKだ。
もし増えていない場合は再起動が必要だが、以下の注意が必要。

  • 空のEFIシステムパーティションを作ってしまったのでブートに失敗する可能性がある
    • ブートデバイスを手動で選択すればブートできるはず
  • 再起動後に /dev/sd[abc…] が入れ替わっている可能性がある
    • 必ず「古いブートデバイスを探す」をやり直してよく確認すること!

無事に出来たらフォーマットをしていく。
dfコマンドで古いブートドライブの各パーティションのファイルシステムを確認する。

$ df -T
ファイルシス            タイプ   1K-ブロック       使用     使用可 使用% マウント位置
# ブートドライブ以外は省略
/dev/sda1               vfat          102182       7958      94224    8% /boot/efi
/dev/sda2               ext4          491604     195493     266415   43% /boot
/dev/sda3               ext4       136856160   13442692  116391900   11% /

この「タイプ」に合わせて、新しいブートドライブの各パーティションをフォーマットしていく。
基本的には"mkfs.***" に「タイプ」を当てはめればそのファイルシステムでフォーマットできる。

$ mkfs.vfat /dev/sdb1
# 出力は省略
$ mkfs.ext4 /dev/sdb2
# 出力は省略
$ mkfs.ext4 /dev/sdb3
# 出力は省略

いよいよファイルコピー

これからのの作業は、使用しているLinuxディストリビューションのインストールディスクなりLive USBメモリなりを用意して、そこからブートして行う必要がある。
使っているディストリビューションにレスキューモードが用意されていれば、

新旧ブートドライブを探す

まずはディスクの一覧を見る。

$ sudo ls /dev/sd*
/dev/sda /dev/sda1 /dev/sda2 /dev/sda3 /dev/sdb /dev/sdb1 /dev/sdb2 /dev/sdb3
/dev/sdc /dev/sdc1

そして /dev/sd[abc…] それぞれをgdiskで表示して新旧ブートドライブを特定する。

$ sudo gdisk /dev/sda
GPT fdisk (gdisk) version 1.0.4

Partition table scan:
  MBR: protective
  BSD: not present
  APM: not present
  GPT: present

Found valid GPT with protective MBR; using GPT.
Command (? for help): p
Disk /dev/sda: 312581808 sectors, 149.0 GiB
Model: INTEL SSDSC2BB16
Sector size (logical/physical): 512/4096 bytes
Disk identifier (GUID): 7F41B9E9-BAE1-4F38-8C13-2CD6725320C3
Partition table holds up to 128 entries
Main partition table begins at sector 2 and ends at sector 33
First usable sector is 34, last usable sector is 312581774
Partitions will be aligned on 2-sector boundaries
Total free space is 1679 sectors (839.5 KiB)

Number  Start (sector)    End (sector)  Size       Code  Name
   1            2048          206847   100.0 MiB   EF00  EFI System Partition
   2          206848         1230847   500.0 MiB   8300  Linux filesystem
   3         1230848       312580095   148.5 GiB   8300  Linux filesystem

この例では /dev/sda が古いブートドライブだ。
同様に残りの /dev/sd[bc…] も確認する。

以下は

  • 古いブートドライブ: /dev/sda
  • 新しいブートドライブ : /dev/sdb

だったとして記載する。前の作業とは名前が変わっていることも多いので要注意。

各パーティションをマウントしてコピーする

特定した各パーティションをマウントしてコピーする
なお、Codeが"EF02"のパーティションはこの方法ではコピーできない。後述の「Codeが"EF02"のパーティションをコピーする」を参照。

# 手動マウントはどこでもできるけど /mnt にフォルダを作るのがお約束
$ cd /mnt

# 古いブートドライブの /boot/efi をマウント
# フォルダ名はなんでもいいけど事故防止のためわかりやすくしよう
$ sudo mkdir efi_old
$ sudo mount /dev/sda1 efi_old

# 新しいブートドライブの /boot/efi をマウント
$ sudo mkdir efi_new
$ sudo mount /dev/sdb1 efi_new

# コピーするよ!
# efi_old の「中身を」efi_newにコピー
$ sudo rsync -aHAXxSvP efi_old/ efi_new/

rsyncのオプションはググれば出てくるが、概ね「ファイルシステムをそっくりそのままコピーし(aHAXxS)、進捗を表示する(vP)」という意味。
オプションの文字の順番は問われないが、大小文字は区別されるので間違えないように。
また"efi_old/"の最後の"/"を付け忘れると、efi_new の中に efi_old というフォルダが作られてその中にコピーされてしまうので必ずつける必要がある。

残りのパーティションも同様にコピーする。

# /boot をコピー
$ sudo mkdir boot_old
$ sudo mount /dev/sda2 boot_old
$ sudo mkdir boot_new
$ sudo mount /dev/sdb2 boot_new
$ sudo rsync -aHAXxSvP boot_old/ boot_new/

# / (ルートパーティション)をコピー
$ sudo mkdir root_old
$ sudo mount /dev/sda3 root_old
$ sudo mkdir root_new
$ sudo mount /dev/sdb3 root_new
$ sudo rsync -aHAXxSvP root_old/ root_new/

Codeが"EF02"のパーティションをコピーする(あった場合のみ)

Ubuntuをデフォルトの設定でインストールするとあったりする。これもブートに必要なのでコピーする。
このパーティションはddでコピーする必要がある。

# 古いブートドライブの"EF02"なパーティションが /dev/sda1 で
# 新しいブートドライブの"EF02"なパーティションが /dev/sdb1 の場合の例
# もちろん自分の環境に合わせて読み替えること

$ sudo dd if=/dev/sda1 of=/dev/sdb1

さらにGRUBを新しいブートドライブにインストールする必要がある。
このコマンドはディストリビューションによって異なる。例えばUbuntu 18.04ではgrub-install("2"がない)だったりする。

# 新しいブートドライブが /dev/sdb の場合
$ sudo grub2-install /dev/sdb

「新しいブートドライブの」/etc/fstab を編集する

ddでディスクコピーをした場合とは異なり、/etc/fstabを編集しないとブートに失敗する。
「新しいブートドライブの」 /etc/fstab を編集する必要がある。

その前に各パーティションのUUIDをメモしておく。blkidコマンドを使う。
なお、"/"(ルートパーティション) の "PARTUUID" もメモしておく。後で使う。

$ sudo blkid
# 新しいブートドライブ以外は省略
/dev/sdb1: SEC_TYPE="msdos" UUID="2FED-0CE8" TYPE="vfat" PARTLABEL="EFI System Partition" PARTUUID="24dfff22-b893-469d-a94c-dde0d53522bc"
/dev/sdb2: UUID="c1b31131-99e7-41ee-86e2-a2e3e5b46033" TYPE="ext4" PARTLABEL="Linux Filesystem" PARTUUID="7aaf4b56-9de3-464e-87f6-f13a2c0b7eb7"
/dev/sdb3: UUID="7d255831-7a7e-4c39-9c27-a51190b4b12e" TYPE="ext4" PARTLABEL="Linux Filesystem" PARTUUID="b04a09cf-e64e-4385-b74c-d8b4231611f1"

先の例では /mnt/root_new に新しいブートドライブのルートパーティションをマウントしたので
/mnt/root_new/etc/fstab を編集すればいい。

# お好みのテキストエディタで /mnt/root_new/etc/fstab を開く
# nanoとかviとか 例ではviだけど
$ vi /mnt/root_new/etc/fstab

各行は先頭から file system(マウントするパーティション), mount point, type…と並んでいる(詳しくはググって)。
ここでは先頭の"file system"だけ書き換えればよい。
この部分を、blkidコマンドの"UUID"の値に書き換える。
"PARTUUID"を使っても問題なく動くが、どういうわけかLinuxインストーラーはUUIDを使いたがるのでこの例ではそれに倣っておく。

書き換えが終わるとこんな感じになる。

/etc/fstab
# ブートドライブ以外は省略
UUID="7d255831-7a7e-4c39-9c27-a51190b4b12e" /                       ext4    defaults        1 1
UUID="c1b31131-99e7-41ee-86e2-a2e3e5b46033" /boot                   ext4    defaults        1 2
UUID="2FED-0CE8"                            /boot/efi               vfat    umask=0077,shortname=winnt 0 2

新しいブートドライブで起動

PCの電源を切ってから、古いブートドライブやコピー時の起動に使ったUSBメモリを外す。
ただし、GRUBはまだ新しい "/"(ルートパーティション)を知らないので、そのままだとブート途中で止まってしまう。

GRUBで新しいルートパーティションを指定する

GRUBの画面が出ているときに"E"キーを押して、起動コマンドを編集する。
起動時にそれっぽい画面が出ないようなら、BIOSっぽい画面からずっとShiftキーを押しっぱなしにしてると出る…らしい。
起動コマンドからこんな感じの行を探して編集する。

linux    /boot/vmlinuz-5.0.17-300.fc30.x86_64 root=PARTUUID=b04a09cf-e64e-4385-b74c-d8b4231611f1 console=tty1

先にblkidコマンドで確認した "/"(ルートパーティション)のPARTUUIDを、このように root=*** の部分に入れてあげればいい。
/etc/fstabではUUIDを""で囲っていたが、ここのPARTUUIDは囲わない。
最初から UUID=**** などとなっていたらUUIDを入れれば多分動く。
また、GRUBは日本語キーボードに対応していない。日本語キーボードで"="を入力するには、その右隣にある"^"キーを押す必要がある。

編集が終わったら、Ctrl+X を押してブートを開始させる。

GRUBの設定を更新する

無事に新しいブートドライブから起動したら、最後にGRUBに新しいルートパーティションを覚えさせる。
これはディストリビューションによってコマンドが異なるので調べること。例はFedora30の場合である。

$ sudo grub2-mkconfig -o /etc/grub2-efi.cfg

後処理とか失敗したときとか

/etc/fstabで他のディスクをマウントするようにしてあった場合は再び有効にしよう。

起動に失敗した場合は、再びLive USBメモリ等から起動して、新しいブートドライブの中身を確認しよう。
(gdiskでパーティションテーブルを確認したり、各パーティションを mount して中身を確認したりする。)

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

java側linuxのzipコマンドで圧縮

java側linuxのzipコマンドを呼び出したい場合、ProcessBuilderを利用できます。
例1:
全部ディレクトリ保持の場合、
List commandList = new ArrayList();
commandList.add("-r");
ProcessBuilder pb =new ProcessBuilder(commandList);

例2:
ディレクトリ保持しない場合、(同じファイル名あれば、エラー)
List commandList = new ArrayList();
commandList.add("-j");
ProcessBuilder pb =new ProcessBuilder(commandList);
LINUXのzipコマンド一覧
-f freshen: only changed files
-u update: only changed or new files
-d delete entries in zipfile
-m move into zipfile (delete OS files)
-r recurse into directories
-j junk (don't record) directory names
-0 store only
-l convert LF to CR LF (-ll CR LF to LF)
-1 compress faster
-9 compress better
-q quiet operation
-v verbose operation/print version info
-c add one-line comments
-z add zipfile comment
-@ read names from stdin
-o make zipfile as old as latest entry
-x exclude the following names
-i include only the following names
-F fix zipfile (-FF try harder)
-D do not add directory entries
-A adjust self-extracting exe
-J junk zipfile prefix (unzipsfx)
-T test zipfile integrity
-X eXclude eXtra file attributes
-y store symbolic links as the link instead of the referenced file
-e encrypt
-n don't compress these suffixes

例3下記の場合はどうする?
フォルダの形式:/home/AB/CD/+各種ファイルとサブフォルダ
入力パース
/home/AB/CD/
圧縮後(/home/AB/CD/含まない)
各種ファイルとサブフォルダ.zip
試して、下記のコマンドはいいです。

pb = new ProcessBuilder("sh", "-c", “zip -r test.zip ./*”)).directory(new File("/home/AB/CD/"));
同じく書きの書き方でもいいです。
pb = new ProcessBuilder("/bin/sh", "-c", “zip -r test.zip ./*”)).directory(new File("/home/AB/CD/"));
pb = new ProcessBuilder("/bin/bash", "-c", “zip -r test.zip ./*”)).directory(new File("/home/AB/CD/"));

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

Ultra96 向け Debian8/GNU Linux でAXI I/F のデータのビット幅を変更する

はじめに

Zynq UltraScale+ MPSoC(ZynqMP) の PS-PL Interface は Fig.1 のように12本あります。そのうちの10本はデータのビット幅を 32bit、64bit、128bit から選択出来ます。

Fig.1 ZynqMP の PS-PL Interface

Fig.1 ZynqMP の PS-PL Interface


これら AXI I/Fのデータのビット幅の変更は、通常、PL 側をビルドするときに指定して、それに対応した FSBL(First Stage Boot Loader) を使ってブートすることで行われます。しかし、『Ultra96 向け Debian GNU/Linux (v2018.2版) ブートイメージの提供』(@Qiita)で紹介したような汎用の FSBL を使って Linux を起動してから Device Tree Overlay を使って PL 側のコンフィギュレーションを行うような場合には使えません。

この記事では、Device Tree を使って AXI I/F のデータのビット幅を変更する方法を紹介します。

Xilinx の AFI デバイスドライバ

実は、Xilinx が提供している Linux のディストリビューション(linux-xlnx)には、ZynqMP の AXI I/F のデータ幅を変更するデバイスドライバがすでに存在します。名前は xilinx-afi です。

ソースコードは drivers/fpga/xilinx-afi.c です。menu config などで、CONFIG_XILINX_AFI=y にすることで、このドライバが Linux Kernel に組み込まれます。 『Ultra96 向け Debian GNU/Linux (v2018.2版) ブートイメージの提供』(@Qiita)で紹介した Linux Kernel にはすでにこのデバイスドライバが組み込まれています。

xilinx-afi ドライバを使って AXI のデータ幅を設定するには、device tree で次のように指定します。

    afi0: afi0 {
        compatible = "xlnx,afi-fpga";
        config-afi = <0 0>, <1 0>;
    };

device tree にどのような記述をするかは、linux-xlnk の Documentation/devicetree/bindings/fpga/xlnx,afi-fpga.txt に説明があります。以下に引用します。

Xilinx ZynqMp AFI interface Manager
The Zynq UltraScale+ MPSoC Processing System core provides access from PL
masters to PS internal peripherals, and memory through AXI FIFO interface
(AFI) interfaces.
Required properties:
-compatible:        Should contain "xlnx,afi-fpga"
-config-afi:        Pairs of  <regid value >
The possible values of regid and values are
 regid:     Regids of the register to be written possible values
        0- AFIFM0_RDCTRL
        1- AFIFM0_WRCTRL
        2- AFIFM1_RDCTRL
        3- AFIFM1_WRCTRL
        4- AFIFM2_RDCTRL
        5- AFIFM2_WRCTRL
        6- AFIFM3_RDCTRL
        7- AFIFM3_WRCTRL
        8- AFIFM4_RDCTRL
        9- AFIFM4_WRCTRL
        10- AFIFM5_RDCTRL
        11- AFIFM5_WRCTRL
        12- AFIFM6_RDCTRL
        13- AFIFM6_WRCTRL
        14- AFIFS
        15- AFIFS_SS2
- value:    Array of values to be written.
        for FM0_RDCTRL(0) the valid values-fabric width   2: 32-bit,1 : 64-bit ,0: 128-bit enabled
        for FM0_WRCTRL(1) the valid values-fabric width   2: 32-bit,1 : 64-bit ,0: 128-bit enabled
        for FM1_RDCTRL(2) the valid values-fabric width   2: 32-bit,1 : 64-bit ,0: 128-bit enabled
        for FM1_WRCTRL(3) the valid values-fabric width   2: 32-bit,1 : 64-bit ,0: 128-bit enabled
        for FM2_RDCTRL(4) the valid values-fabric width   2: 32-bit,1 : 64-bit ,0: 128-bit enabled
        for FM2_WRCTRL(5) the valid values-fabric width   2: 32-bit,1 : 64-bit ,0: 128-bit enabled
        for FM3_RDCTRL(6) the valid values-fabric width   2: 32-bit,1 : 64-bit ,0: 128-bit enabled
        for FM3_WRCTRL(7) the valid values-fabric width   2: 32-bit,1 : 64-bit ,0: 128-bit enabled
        for FM4_RDCTRL(8) the valid values-fabric width   2: 32-bit,1 : 64-bit ,0: 128-bit enabled
        for FM4_WRCTRL(9) the valid values-fabric width   2: 32-bit,1 : 64-bit ,0: 128-bit enabled
        for FM5_RDCTRL(10) the valid values-fabric width   2: 32-bit,1 : 64-bit ,0: 128-bit enabled
        for FM5_WRCTRL(11) the valid values-fabric width   2: 32-bit,1 : 64-bit ,0: 128-bit enabled
        for FM6_RDCTRL(12) the valid values-fabric width   2: 32-bit,1 : 64-bit ,0: 128-bit enabled
        for FM6_WRCTRL(13) the valid values-fabric width   2: 32-bit,1 : 64-bit ,0: 128-bit enabled
        for AFI_FA(14)
            dw_ss1_sel  bits (11:10)
            dw_ss0_sel  bits (9:8)
                0x0: 32-bit AXI data width),
                0x1: 64-bit AXI data width,
                0x2: 128-bit AXI data
        All other bits are 0 write ignored.
        for AFI_FA(15)  selects for ss2AXI data width valid values
                    0x000: 32-bit AXI data width),
                    0x100: 64-bit AXI data width,
                    0x200: 128-bit AXI data
Example:
afi0: afi0 {
    compatible = "xlnx,afi-fpga";
    config-afi = <0 2>, <1 1>, <2 1>;
};

Xilinx の AFI デバイスツリーのregid とレジスタの対応

前節の Documentation/devicetree/bindings/fpga/xlnx,afi-fpga.txt が分かりづらいのは、regid の説明です。これでは regid が何を意味するのかさっぱり分かりません。そこで Linux Kernel や Firmware のソースコードを追って調べてみました。その際に判明した、regid に対応する ZynqMP Register Module と AXI I/F を次の表に示します。

regid Name Register AXI I/F value
Module Register
0 AFIFM0_RDCTRL AFIFM0 RDCTRL S_AXI_HPC0_FPD 2'b10: 32-bit
2'b01: 64-bit
2'b00: 128-bit
1 AFIFM0_WRCTRL WRCTRL
2 AFIFM1_RDCTRL AFIFM1 RDCTRL S_AXI_HPC1_FPD
3 AFIFM1_WRCTRL WRCTRL
4 AFIFM2_RDCTRL AFIFM2 RDCTRL S_AXI_HP0_FPD
5 AFIFM2_WRCTRL WRCTRL
6 AFIFM3_RDCTRL AFIFM3 RDCTRL S_AXI_HP1_FPD
7 AFIFM3_WRCTRL WRCTRL
8 AFIFM4_RDCTRL AFIFM4 RDCTRL S_AXI_HP2_FPD
9 AFIFM4_WRCTRL WRCTRL
10 AFIFM5_RDCTRL AFIFM5 RDCTRL S_AXI_HP3_FPD
11 AFIFM5_WRCTRL WRCTRL
12 AFIFM6_RDCTRL AFIFM6 RDCTRL S_AXI_LPD
13 AFIFM6_WRCTRL WRCTRL
14 AFIFS FPD_SLCR afi_fs SS0=M_AXI_HPM0_FPD
SS1=M_AXI_HPM1_FPD
SS0_SEL bits[9:8]
SS1_SEL bits[11:10]
2'b00: 32-bit
2'b01: 64-bit
2'b10: 128-bit
15 AFIFS_SS2 LPD_SLCR afi_fs SS2=M_AXI_HPM0_LPD SS2_SEL bits[9:8]
2'b00: 32-bit
2'b01: 64-bit
2'b10: 128-bit

各レジスタの詳細は『Zynq UltraScale+ Devices Register Reference』を参照してください。この資料は以下の URL で示すページが見やすくて良いと思います。

次に device tree overlay を使ってPL のコンフィギュレーションと同時に S_AXI_HPC0_FPD と M_AXI_HPM0_FPD のビット幅を128bit に設定する例を示します。

/dts-v1/; /plugin/;
/ {
    fragment@0 {
        target-path = "/fpga-full";
        __overlay__ {
            firmware-name = "design_1_wrapper.bin";
        };
    };
    fragment@1 {
        target-path = "/amba_pl@0";
        __overlay__ {
            afi0 {
                compatible    = "xlnx,afi-fpga";
                config-afi    = <0 0>, <1 0>, <14 0x200>;
            };
        };
    };
};
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む