mv と cp: 結果のファイルの違いは何ですか?

mv と cp: 結果のファイルの違いは何ですか?

一部のアプリケーションの構成ファイルが適切に含まれていないというバグがあったので、ファイル内の問題のある行を特定するために、古い内容を一度に数行ずつ新しいファイルにコピーしました。

最終的に、ファイルの正確な複製を作成しましたが、古いファイルはまだ動作しませんでしたが、新しいファイルは完全に正常に動作しました。

もっと具体的に言うと、mvコマンドを使用して、ファイルを保存した場所から目的の場所に移動すると、エラーが発生します。 を使用して、cpファイルを目的の場所にコピーすると、エラーは発生しません。

明らかに、、、または、diffのようなファイルは、一方が他方のコピーであるため、2つのファイルの間に違いはありません。filels -lcpファイルの正確なコピーを作成する限り

これは仕事上のことなので、ファイルについてあまり多くの情報を共有することはできません。要するに、コマンドは「異なる」ファイル B を生成します。私の推測では、cp fileA fileBファイルB の非常に低レベルの属性が(同じ動作を生成する場合でも)mv fileA fileB中に残されます。cpcp -p

結果のファイルの正確な内容に関して、mv と cp の違いは何ですか?

編集: ls -l:

-rw-r--r--. 1 root root 3389 Aug  8 22:53 fileA
-rw-r--r--. 1 root root 3389 Aug  8 23:03 fileB

編集: アプリケーションは mysql で、ファイルは .cnf ファイルです。この構成ファイルで特に興味深い項目は、マスター スレーブ データベース レプリケーションで使用されるバイナリ ログの名前です。「エラー」は「バイナリ ログを使用していません」です。これは、その項目が mysql によって「読み取られた」ことがないため、バイナリ ログが存在しないためです。

最初に考えたのは、設定ファイルに構文エラーがあり、それが全体を読み取れない原因になっているということでした。そのため、テキストブロックをコピーして手動で再作成する必要がありました。

編集: 何とかなってきました... ようやくファイルに関して何か変わった点がありました。

ls -lZ

-rw-r--r--. root root unconfined_u:object_r:user_home_t:s0 server.cnf.bad
-rw-r--r--. root root unconfined_u:object_r:mysqld_etc_t:s0 server.cnf.good

答え1

TL;DR: システムではカーネルが使用されている場合、システムによって使用されるファイル(つまりデーモン)は、との代わりにと を使用してコピーcp -aZまたは移動する必要があります。これが行われていない場合は、宛先でまたはを使用して、システムにデフォルトの SELinux コンテキストを復元するように要求する必要があります。mv -Zcp -amvrestorecon -v -rrestorecon -v -F -rrestorecon主要な構成ファイルで動作するスクリプトの最後にあります。

RHELとその派生製品のほとんどデフォルトでSELinuxを使用する

したがって、問題を解決するには、システムがRHELベースでパッケージを使用している場合はmariadb-server、ファイルが正しい場所:

# restorecon -v -F /etc/my.cnf.d/server.cnf
Relabeled /etc/my.cnf.d/server.cnf from unconfined_u:object_r:user_home_t:s0 to system_u:object_r:mysqld_etc_t:s0

(これがないと、設定された に-F変更されないことに注意してください。一般的なシステムでは問題になりません。違いとそれが問題にならない理由についての私の知識は、ここまでには及びません)。unconfined_usystem_u

ファイルに正しいコンテキストを記述するのは、他の場所。chcon次のように実行できます ( などで記述するか-u -t、 で他のファイルからコンテキストをコピーすることでより簡単に実行できます--reference)。

# ls -lZ /home/test/server.cnf.bad
-rw-r--r--. 1 root root unconfined_u:object_r:user_home_t:s0 744 Apr 30  2017 /home/test/server.cnf.bad
# chcon -v -u system_u -t mysqld_etc_t /home/test/server.cnf.bad 
changing security context of '/home/test/server.cnf.bad'
# ls -lZ /home/test/server.cnf.bad
-rw-r--r--. 1 root root system_u:object_r:mysqld_etc_t:s0 744 Apr 30  2017 /home/test/server.cnf.bad

SELinux の問題が疑われる場合は、プロセスまたはファイルに関連する単語を含むエントリを確認してください。/var/log/audit/audit.logdeniedを使用して、SELinux に一時的に操作を許可するように要求し、その後でそれらを復元して動作を比較することができます。特に本番環境では、のままにしないでください。setenforce Permissivesetenforce EnforcingPermissive

以下に様々な説明をします。

設定ファイルで作業する場合の例と実行すべきこと

cpさまざまなオプションとmvSELinux 対応システムでの動作の例:

$ id
uid=1034(test) gid=1034(test) groups=1034(test)
$ pwd
/home/test
test@glasswalker:~$ ls -lZ foo
-rw-r--r--. 1 test test unconfined_u:object_r:user_home_t:s0 0 Aug 11 11:25 foo
$ cp foo /tmp/foo1
$ cp --preserve=context foo /tmp/foo2
$ cp -a foo /tmp/foo3
$ cp -aZ foo /tmp/foo4
$ mv foo /tmp/foo5
$ ls -lZ /tmp/foo?
-rw-r--r--. 1 test test unconfined_u:object_r:user_tmpfs_t:s0 0 Aug 11 11:25 /tmp/foo1
-rw-r--r--. 1 test test unconfined_u:object_r:user_home_t:s0  0 Aug 11 11:25 /tmp/foo2
-rw-r--r--. 1 test test unconfined_u:object_r:user_home_t:s0  0 Aug 11 11:25 /tmp/foo3
-rw-r--r--. 1 test test unconfined_u:object_r:user_tmpfs_t:s0 0 Aug 11 11:25 /tmp/foo4
-rw-r--r--. 1 test test unconfined_u:object_r:user_home_t:s0  0 Aug 11 11:25 /tmp/foo5
$ touch bar
$ ls -lZ bar
-rw-r--r--. 1 test test unconfined_u:object_r:user_home_t:s0 0 Aug 11 11:49 bar
$ mv -Z bar /tmp
$ ls -lZ /tmp/bar
-rw-r--r--. 1 test test unconfined_u:object_r:user_tmpfs_t:s0 0 Aug 11 11:49 /tmp/bar

したがって、セキュリティ コンテキストが重要であり、他の属性も保持される場合は、cp -aZまたは を使用mv -Zするとうまく機能します。システム ファイルを移動するスクリプトでは、常にまたはコマンド-Zの オプションを使用するか、予期しない問題を回避するために最終ステップでを使用するだけです。cpmvrestorecon

なぜそのような違いがあるのでしょうか?

このmvコマンドは、一貫した動作を維持します。同じファイルシステムで実行された場合、もちろん、セキュリティ コンテキストを含むファイルに添付されているものはすべて変更されません。これは単なる「名前の変更」だからです。したがって、2 つのファイルシステム間では、実際にはコピーしてから削除することになりますが、一貫性を保つために、セキュリティ コンテキストを含むファイルに添付されていて認識されているものはすべて変更せずにコピーします。

cpデフォルトでは、コマンドは作成する新しいファイルなので、このファイルは、 で別途指定されない限り、通常どおり親の selinux コンテキストを継承します。--preserve=contextは に含まれています。は オプションを使用してから減算できるため、 SELinux が重要な場合は、樹形全体をコピーするときに の代わりにを使用するのが最善策です。-a--preserve=context-a-Z-aZ-a

通常の場合、ファイルを作成すると、この新しいファイルはディレクトリのSELinuxコンテキストを継承するため、すべて正常に動作します(話題から外れますが、まれに、名前のルールのため、ファイルのコンテキストがディレクトリのコンテキストと異なる必要がある場合がありますが、カーネルは気にしません。デーモンなどのプログラムでは、restorecond処理するために必要になります。

SELinuxとは

SELinuxは強制アクセス制御メカニズム(別名マック) は他のすべてのメカニズム(UNIXパーミッション、別名DACアクセス制御リスト、別名ACLプロセスがプロセスセキュリティコンテキストで実行される場合、これがプロセスコンテキストは要求された操作(開く、読む、書く、mmapなど)を実行できる。ファイル作業しようとするコンテキスト。

OP の場合の例:mysqldのプロセス コンテキストが、 を含むいくつかのファイル コンテキスト タイプにのみアクセスできる場合、間違ったタイプの構成ファイルを読み取ることができないため、起動は失敗mysqld_etc_tuser_home_tます。mysqlduser_home_t

通常のシステムでは、対話型/ログインユーザーにとってはこれは問題になりません。なぜなら、通常のプロセスコンテキストは制限されていないため、SELinuxルールは適用されないからです。systemdまたは他の同様のメカニズムによって起動されたすべてのデーモンは、意思プロセスコンテキストを受け取ります。これはps-Zオプションで確認できます。SELinux を実行している Debian システムの例:

# ps -Z -p $$
LABEL                             PID TTY          TIME CMD
unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c1023 22498 pts/7 00:00:00 bash
# ps -Z -p $(pidof /sbin/getty)
LABEL                             PID TTY      STAT   TIME COMMAND
system_u:system_r:getty_t:s0     6158 tty1     Ss+    0:00 /sbin/getty 38400 tty1
system_u:system_r:getty_t:s0     6159 tty2     Ss+    0:00 /sbin/getty 38400 tty2
system_u:system_r:getty_t:s0     6160 tty3     Ss+    0:00 /sbin/getty 38400 tty3
system_u:system_r:getty_t:s0     6161 tty4     Ss+    0:00 /sbin/getty 38400 tty4
system_u:system_r:getty_t:s0     6162 tty5     Ss+    0:00 /sbin/getty 38400 tty5
system_u:system_r:getty_t:s0     6163 tty6     Ss+    0:00 /sbin/getty 38400 tty6

答え2

はい、主な違いがあります。

  • cpはファイルのコピーを作成します
  • mv (ファイルシステム内に留まる場合) は、ディスク上のいくつかのポインターを移動するだけです。

次のことを試してください。

touch a
ls -i a
cp a b
ls -i a b
mv a c
ls -i b c

b は新しい inode 番号を持つ新しいファイルであるのに対し、c は古い a の inode 番号を持つ同じファイルであることがわかります。

それでも、あなたの奇妙な行動を説明することはできません。

答え3

これは何5月何が起こっているのか(アプリケーションやこれらのエラーに関する情報はほとんど共有されていないため、推測することしかできません)。

Linuxの場合強制的なファイルロックは一般的ではない. 次のような呼び出しflock(2)管理勧告ロック。つまり、カーネルはロックを追跡しますが、それを強制することはなく、ロックに従うかどうかはアプリケーション次第です。

fileA何かがロックされ、アプリケーションがロックに従う場合、サービスを拒否する可能性があります。これが起こると仮定しましょう。

ロックはパスや名前ではなく、inode に影響します。ロックされたファイルfileAfileB単一のファイルシステム内で移動 (名前変更) しても、inode には影響がなく、ファイルはロックされたままで、アプリケーションは引き続きそのファイルで動作しません。ファイルをコピーすると、fileBロックされていない独自の inode を持つ別のファイルが作成され、アプリケーションは動作します。

(注: ファイルを別のファイルシステムに移動すると、実際にはコピーと削除が行われるため、ロックがある場合は解除されるはずです)。

関連情報