하드 링크 사용 사례? [닫은]


40

어떤 상황에서 소프트 링크가 아닌 하드 링크를 사용하고 싶습니까? 필자는 개인적으로 소프트 링크를 통해 하드 링크를 사용하고 싶었던 상황을 겪어 본 적이 없으며 웹을 검색 할 때 발견 한 유일한 유스 케이스는 동일한 파일을 중복 제거합니다 .


4
아래에는 좋은 답변이 있지만 (매끄러운) 역사적 맥락을 고려하십시오. 유닉스가 새로 출시되었을 때 디스크 드라이브는 느리고 용량과 버퍼링이 제한되었습니다. 하드 링크는 단순히 파일 시스템에서 동일한 파일에 대한 또 다른 직접 항목이었습니다. ls 에 액세스하든 전화를 걸었 든 list 와 관련이 없습니다. 당신이 만든 더라면 목록을 소프트 링크를, 그것의 사용이라는 특수 파일 읽기, 디렉토리에 그것을 찾는 포함 할 목록을 사용자가 파일의 원하는 것을 볼, LS를 찾을 LS 디렉토리를, 실제 읽어 LS의 디스크에서 파일을. 성능 의 차이!
RichF

16
파일에 대한 첫 번째 하드 링크는 매우 유용합니다.
Harming Monica 중지

@OrangeDog : 예. 그러나 여러 개의 링크를 지원하려면 inode에 링크 카운트 필드 만 있으면됩니다. (연결되지 않았지만 여전히 열려있는 경우를 처리하려면 메모리 내 버전의 inode에 플래그가 필요할 수 있습니다. 저널링없이 충돌 한 후에도 fsck는 여전히 링크가없는 inode를 찾아야합니다.
Peter Cordes

1
POSIX 디렉토리 의미는 다르게 설계되어야합니다. ..항상 .상위 디렉토리 와 동일한 inode 입니다. 상황이 좋아 find잎 디렉토리를 감지하는 링크 카운트 = 2를 확인할 수 있으며 피하기는 stat하위 디렉토리를 찾기 위해가 readdir에서 항목을 보내고. 그러나 이는 비 디렉토리 파일 (일반, 심볼릭 링크, 장치, 소켓 및 명명 된 파이프)의 하드 링크를 지원함으로써 가능한 작은 기능입니다. (예, 심볼릭 링크에는 자체 inode가 있으며 하드 링크 될 수 있습니다.)
Peter Cordes

1
하드 링크를 사용하는 한 가지 이유는 "글로벌"특성에 대한 SO 검토에서 보지 못했습니다. 파일이 일반적으로 작은 파일 시스템 (대부분 짧은 메모)을 상상해보십시오. 그러나 일을 체계적으로 유지하려면 다른 위치에있는 동일한 파일에 대한 포인터가 필요할 수 있습니다. 심볼릭 링크를 사용하면 각 포인터가 inode를 사용합니다. 이러한 파일 시스템에는 이미 inode가 부족한 문제가있을 수 있습니다. 하드 링크를 포인터로 사용하면이 문제에 도움이됩니다. inode의 수는 제한되어 있습니다. 그것들의 이름은 (적어도 같은 방식으로) 아닙니다.
mathguy

답변:


27

BTRFS 볼륨의 스냅 샷도 포함하고있는 다른 의견에서 언급 한 백업 사용량 외에도 소프트 링크를 통한 하드 링크의 사용 사례는 태그로 분류 된 파일 모음입니다. (컬렉션을 생성하는 가장 좋은 방법은 아니지만 데이터베이스 기반 방법이 더 나을 수 있지만 합리적으로 안정된 간단한 컬렉션의 경우에는 나쁘지 않습니다.)

모든 파일이 하나의 플랫 디렉토리에 저장되고 연도, 주제, 아티스트, 장르 등 다양한 기준에 따라 다른 디렉토리로 분류되는 미디어 콜렉션. 개인 영화 콜렉션 또는 상업 스튜디오의 집단 일 수 있습니다. 공장. 본질적으로 완료되면 파일은 링크를 통해 여러 위치에 수정 및 정렬되지 않은 상태로 저장됩니다.

"원본"및 "복사"의 개념은 하드 링크에 적용 할 수 없습니다. 파일 대한 모든 링크 는 원본이며 일반적인 의미에는 "복사"가 없습니다. 그러나 유스 케이스에 대한 설명을 위해이 용어는 동작의 논리를 모방합니다.

"원본"은 "카탈로그"디렉토리에 저장되고 정렬 된 "복사본"은 해당 파일에 하드 링크됩니다. 정렬 디렉토리의 파일 속성을 r / o로 설정하면 파일 이름 및 정렬 된 구조가 실수로 변경되는 것을 방지 할 수 있으며 카탈로그 디렉토리의 속성은 r / w가되어 필요에 따라 수정할 수 있습니다. (일부 플레이어는 사용자 입력 또는 인터넷 검색에서 미디어 파일에 포함 된 태그를 기반으로 파일의 이름을 바꾸고 파일을 재구성하려고 시도하는 음악 파일입니다.) 또한 "복사"디렉토리의 속성이 다를 수 있기 때문에 "원본"디렉토리, 정렬 된 구조는 그룹 또는 세계에서 액세스가 제한 될 수 있지만 주 "카탈로그"는 주 사용자 만 액세스 할 수 있습니다. 모든 권한으로. 그러나 파일 자체는 항상 해당 inode에 대한 모든 링크에서 동일한 속성을 갖습니다. (ACL은 내 지식 영역이 아니라 그것을 향상시키기 위해 탐구 될 수 있습니다.)

원본의 이름을 바꾸거나 이동 한 경우 (예를 들어 단일 "카탈로그"디렉토리가 너무 커서 관리하기에는 너무 커짐) 하드 링크가 유효한 상태로 유지되고 소프트 링크가 끊어집니다. "복사본"이 이동되고 소프트 링크가 상대적이면 소프트 링크가 다시 끊어지고 하드 링크가되지 않습니다.

참고 : 소프트 링크가 관련된 경우 다른 도구가 디스크 사용을보고하는 방법에 불일치가있는 것 같습니다. 그러나 하드 링크를 사용하면 일관성이있는 것 같습니다. 따라서 카탈로그에 100 개의 파일이 "태그"모음으로 정렬되어 있으면 500 개의 "복사본"이 쉽게 연결될 수 있습니다. (예 : 사진, 날짜, 사진사 및 평균 3 개의 "제목"태그라고 말하십시오.) 예를 들어, 돌고래는 하드 링크 용 파일 100 개, 소프트 링크를 사용하는 경우 600 개 파일로보고합니다. 흥미롭게도 동일한 디스크 공간 사용 방식을보고하므로 소프트 링크를위한 작은 파일 모음과 하드 링크를위한 작은 파일 모음처럼 보입니다.

이러한 유형의 유스 케이스에 대한주의 사항은 COW를 사용하는 파일 시스템에서 "원본"을 수정하면 하드 링크를 끊을 수 있지만 소프트 링크를 끊을 수는 없다는 것입니다. 그러나 편집, 저장 및 정렬 후 마스터 사본을 보유하려는 경우 COW는 시나리오에 들어 가지 않습니다.


3
참고 : btrfs 스냅 샷은 하드 링크가 아닙니다. 서로 다른 동작을합니다 (예 : 한 복사본을 수정해도 다른 복사본은 수정되지 않음). 그리고 stat하나의 링크 만 표시합니다.
derobert

@derobert 스냅 샷의 작동 방식을 잘 모르지만 약간의 조사만으로도 흥미로운 점이 드러납니다. 변경되지 않은 파일 / 디렉토리의 stat경우 동일한 inode 번호가 표시되지만 장치 ID는 다릅니다. 서브 볼륨이 거의 장착되지 않은 메인 볼륨에 겹쳐지는 방식과 관련이 있어야합니다. 주 볼륨이 마운트 된 경우 stat해당 버전의 파일을 보유한 스냅 샷 수와 동일한 링크 수가 표시 될 것으로 생각 됩니다. COW는 아마도 다른 것에 영향을 미치지 않는 수정 한 것을 돌볼 것입니다. 온화한 호기심에 근거한 단순한 추측이지만 더 깊이 파고 들기에는 호기심이 없습니다.
집시 Spellweaver

각 symlink에는 고유 한 inode가 있으므로 파일 시스템에서 inode 항목을 사용합니다. 기존의 Unix 파일 시스템에서는 XFS처럼 필요에 따라 할당하지 않고 FS 생성시 inode에 예약 할 공간을 선택해야합니다. 따라서 symlink 버전이 VFS 캐시 풋 프린트 관련 사항을 포함하여 더 많은 inode를 사용하는 것이 실제로 중요합니다.
Peter Cordes

23

하드 링크는 두 파일의 존재를 묶고 싶지 않은 경우에 유용합니다. 이걸 고려하세요:

touch a
ln -s a b
rm a

이제는 b쓸모가 없습니다. (이러한 단계는 아주 멀리 떨어져 있거나 다른 사람들에 의해 수행 될 수 있습니다.)

하드 링크가있는 반면

touch a
ln a b
rm a

b 여전히 존재하고 정확합니다.


8
@MatthewCline 효율적인 증분 백업을 관리 할 때이 동작을 원할 것입니다. 특히 오래된 백업이 삭제되면 소프트 링크 기반 백업 시스템에서 모든 최신 백업 파일 / 링크를 유효한 기반으로 다시 확인하고 다시 연결해야하지만 하드 링크는 해당 작업을 inode 수준에서 "무료"로 수행합니다. 예를 들어 타임 시프트 / 백인 시간은 하드 링크를 광범위하게 사용합니다.
orzechow

3
@orzechow 백업 시스템 근처에서 하드 링크 동작을 원한다고 생각하지 않습니다. github.com/bit-team/backintime/wiki/… backintime은 파일에 대한 모든 변경 사항이 업데이트되지 않고 제거-생성주기에 의한 것이라고 어리석게 가정합니다.
DepressedDaniel

10
@DepressedDaniel 하드 링크는 백업 시스템 에서 잘 작동 하므로 백업을 라이브 파일에 하드 링크하기를 원하지 않습니다. 그러나 어떠한 경우에도 라이브 시스템에서 직접 백업에 접근 할 수 없어야합니다 ...
Stephen Kitt

1
이것은 대답이 아닙니다. 구체적으로 유스 케이스가 아닙니다. 하드 링크 동작의 데모 일뿐입니다.
user394

1
@ ThomasPadron-McCarthy 그건 오해입니다. BiT는 하드 링크 만 사용하여 다른 스냅 샷 내에서 동일한 파일을 링크합니다. 원본 파일에 연결되어 있지 않습니다! (나는 BiT 개발자입니다)
Germar

11

단일 프로그램은 실행되는 이름에 따라 동작을 변경할 수 있습니다.

$ ls -li `which pgrep` `which pkill`
208330 -r-xr-xr-x  2 root  bin  19144 Jul 26  2016 /usr/bin/pgrep
208330 -r-xr-xr-x  2 root  bin  19144 Jul 26  2016 /usr/bin/pkill

소스 에서 어느 것이 다음과 같은 것을 통해 결정됩니다.

if (strcmp(__progname, "pgrep") == 0) {
    action = grepact;
    pgrep = 1;
} else {
    action = killact;

정확한 세부 사항은 관련된 OS 및 언어에 따라 다릅니다.

이를 통해 (대부분) 동일한 코드를 2 개의 (대부분) 동일한 바이너리로 컴파일 할 필요가 없습니다. APUE의 Stevens에 따르면 4 장 심볼릭 링크가 BSD4.2 (1983)에 구현되어 하드 링크의 다양한 제한을 대체하기는하지만 유닉스는 디스크 공간이 너무 비싸던 시절로 거슬러 올라갑니다. 프로그램 이름으로 심볼릭 링크 이름이 사용되는지 확인하는 테스트 프로그램은 다음과 같습니다.

#include <stdio.h>
#include <stdlib.h>
int main(int argc, char *argv[])
{
    printf("called as '%s'\n", *argv);
    exit(0);
}

그리고 다음을 통해 테스트되었습니다.

$ cc -o myname myname.c 
$ ln -s myname alias
$ ./myname
called as './myname'
$ ./alias
called as './alias'
$ 

4
그러나 일반적으로 소프트 링크로 처리되지 않습니까?
Matthew Cline

1
@MatthewCline은 오늘날에도 가능하지만 APUE의 Stevens에 따르면 4.2BSD (1983) 이전에는 심볼릭 링크가 존재하지 않았습니다.
thrig jan

4
@thrig, 질문은 특히 심볼릭 링크를 사용하여 수행 할 수 없거나 심볼릭 링크를 사용하는 것보다 바람직하지 않은 사용 사례를 묻습니다. 귀하의 답변은 HL과 SL 모두에 적용됩니다.
Marcelo

3
BusyBox는 이것을 최대로 가져옵니다.
Max Ried

8

내 P2P 소프트웨어가 특정 파일 다운로드를 마치면 파일이 특정 디렉토리에 저장됩니다. 다운로드 한 파일은 거의 편집 할 필요가 없습니다. 일반적인 경우는 파일이 필요한 다른 디렉토리에 하드 링크를 만드는 것입니다.

장점 :

  • 본인 rm이나 mv"복사" 하더라도 P2P 네트워크에서 파일을 계속 공유합니다 .
  • 파일은 내가 필요한 경로에 있습니다. 이러한 위치의 대부분은 공유되지 않습니다.
  • 내가 할 수 rm은 "원래는"파일 공유를 중지합니다; 이 작업은 원하는 위치의 "복사"에 영향을 미치지 않습니다.
  • 내 디스크 공간은 한 번만 사용됩니다.

요점 : 내가 먼저 어떤 파일을 먼저 알고 있는지를 알고 있다면 rmsymlink를 사용할 수 있습니다. 그러나 나는 모른다.


6

파일 시스템은 파일을 구성하고 분류하는 간단하면서도 효율적인 방법입니다 (이것이 가장 중요한 존재 이유). 하드 링크는이 문제에서 더 높은 수준의 유연성을 허용합니다.

언급 한 바와 같이, 하드 링크를 다룰 때 원본과 사본에 대한 개념이 없으며, 모든 디렉토리 항목 (하드 링크)은 우선 순위가없는 파일의 존재 (아이 노드를 가리킴)에 대한 참조 일 뿐이므로 깨진 하드 링크도 없습니다. .

따라서 여기에는 하드 링크가 참석 하지만 소프트 링크가 참여 하지 않는 사용 사례가 있습니다 .

  1. 영화 나 음악 또는 기타 미디어 모음이 있고 지사에서 아티스트별로 분류 한 노래와 같이 다른 분류 기준을 적용하려고한다고 가정합니다 (각 아티스트에는 자체 하위 디렉토리가 있음). 다른 브랜치 (각각 다른 서브 디렉토리에있는)의 장르별로 링크가 끊어지지 않도록 이동시 파일을 관리하고 다시 연결하십시오.

  2. 또 다른 이유는 동일한 파일의 여러 사본을 보유하는 데 필요한 스토리지 공간 낭비를 피하고 chrootsyscall이 "마스터"파일 시스템 루트에있는 파일의 서브 세트로부터 이익을 얻을 수 있도록하기 위한 것입니다 (심볼릭 링크는 외부에서 파일을 참조 할 수 없음) chroot샌드 박스, 그들은) 상대 경로를 경우에도.

  3. 하드 링크가 존재하는 또 다른 중요하지만 거의 언급되지 않은 이유는 ..하위 디렉토리입니다. ..디렉토리는 실제로 하드 링크의 존재를 매우 쉽게 구현할 수 있도록이 만드는 동안 하드 링크하지 않고는 완전히 다른 방식으로 구현되어야한다, (대부분의 유닉스 구현을 내지 fs) 상위 디렉토리에 하드 링크입니다.


1
포인트 1의 경우, uuid를 파일의 '정식'이름으로 사용하고 사람이 읽을 수있는 모든 이름을 uuid에 대한 심볼릭 링크로 만드는 것이 대체 솔루션입니다.
R ..

UUID의 제안은 학문적으로 정확하지만 파일 이름에 UUID를 사용하는 것은 실용적이지 않으며 다시 말하지만, 목표는 사물을 단순화하는 것이지, 더 어렵거나 "사람이 이해할 수없는"것을 만드는 것입니다. 게다가, "정식"파일 참조를위한 uudis를 갖는 것은 실제 파일 inode에 대한 추가적인 간접적 인 것일 뿐이므로,이 접근 방식에서는 이점이없고, 성능에 미치는 영향, "이상한"이름을 가진 파일들이 많이있는 더 많은 디렉토리 엔트리를 저장하기위한 디스크 공간 ...
Marcelo

5

하드 링크가 필요한 매우 일반적인 실제 예 :

git clone --reference <repository>

이것은 거의 제로 복사로 로컬 Git 리포지토리에서 복제합니다. 객체 파일 ( "데이터베이스"를 위해 Git이 사용하는 불변 파일)을 복사하는 대신 단순히 하드 링크합니다.

모든 저장소는 객체를 제거 할 수 있지만 inode는 나머지 저장소에 유효합니다. 그리고 모든 저장소에서 객체가 제거되면 디스크에서 삭제됩니다. 하드 링크는 아름답고 강력하고 빠른 솔루션을 만듭니다. CI 서버에서 매우 일반적입니다.


하드 링크가 아닌 버전이 있습니다 : git clone --shared <repository>. 그러나 모든 사람들이 같은 디렉토리에서 작업하고 있기 때문에 이것은 까다 롭고 더 많은 경고가 있습니다.


4

최근에 부팅 uImage할 이미지를 가리키는 소프트 링크 인 U-Boot 기반 시스템에 대해 다소 안전한 업데이트 절차를위한 유스 케이스를 사용 했습니다. 파일 시스템이 작동한다고 가정하면 프로세스가 진행됩니다.

ln image.bin backup_image.bin
ln -sf backup_image.bin uImage

// replace image.bin

ln -sf image.bin uImage
rm backup_image.bin

하드 링크가 없으면 그렇게 간단하지 않습니다.

/편집하다:

의견 덕분에 이제는 더 잘하는 것이 좋습니다.

ln image.bin backup_image.bin
ln -sf backup_image.bin uImageNew
mv uImageNew uImage || rm -rf uImage && mv uImageNew uImage

// replace image.bin

ln -sf image.bin uImageNew
mv uImageNew uImage || rm -rf uImage && mv uImageNew uImage
rm backup_image.bin

( rm예를 들어 uImage예기치 않은 무언가가 mv실패 할 경우 [이전의 ln -sf해결책 은 아님 ]) 이상한 상태를 더 잘 피할 수 있도록 여기에 있습니다 .


2
+1 이것은 개념적으로 매우 좋은 이유이지만 불행히도 ln -sf원자 적이 지 않기 때문 입니다. 이전 심볼릭 링크를 삭제하고 새로 만듭니다. 이 문제를 해결하려면 임시 이름으로 새 심볼릭 링크를 만들고 교체하려는 심볼 이름으로 rename(2)( mv) 연결해야합니다.
R ..

@R .. 네 말이 맞아! 😲 stat("uImage", {st_mode=S_IFREG|0777, st_size=0, ...}) unlink("uImage"),symlink("backup_image.bin", "uImage")
phk

1
BTW, install.sh문제를 해결하는 내 버전은 여기를 참조하십시오 : git.musl-libc.org/cgit/musl/tree/tools/install.sh
R ..

@R .. 대상이 이미 symlink 루프의 일부인 symlink와 같이 이미 존재하는 경우 mv에도 with -f가 실패 할 수 있습니다. 데모 :ln -sf foo bar; ln -sf bar foo; echo "Before:"; ls -l foo bar; >testfile; mv testfile foo || { echo "Using mv -f"; mv -f testfile foo; }; echo "After:"; ls -l foo bar
phk

3

하드 링크에 사용했던 한 가지 용도는 손상된 파일을 다운로드하거나 압축을 풀 때입니다. 압축 해제 또는 압축 해제와 같은 다운로드 또는 압축 해제를 수행하는 프로그램은 종종 오류가 발생하면 불완전한 파일을 자동으로 제거하며 일반적으로 유지할 옵션이 없습니다. 파일을 유지하려면 하드 링크를 만들 수 있습니다.


3

BackupPC 는 서버에서 하드 링크를 사용하여 파일 수준 중복 제거를 제공하는 백업 시스템입니다.

파일은 먼저 md5 해시를 기반으로 "풀"디렉토리 트리에 저장됩니다. 해당 파일을 사용하는 모든 백업은 풀 파일에 대한 하드 링크를 만듭니다. 백업이 만료 / 삭제되면 하드 링크가 파일 시스템에서 제거됩니다.

하드 링크는 자동 참조 카운트를 제공하기 때문에 소프트 링크보다 우수합니다. 크론 작업은 풀 디렉토리에서 둘 이상의 링크가없는 파일을 주기적으로 삭제합니다.

이 방법에는 몇 가지 단점이 있지만 (주로 파일 시스템 기반 도구를 사용하여 백업 저장소를 복제하는 것이 어렵다는) 단점이 있지만 실제로는 매우 강력합니다.


또 다른 사용 사례 : Tomcat Java 웹 응용 프로그램 서버는 파일 이름을 메타 데이터로 취급합니다. Java "war"파일은 웹 서버의 경로를 기반으로 이름을 지정해야합니다.

예 : foo.war URL을 제공하는 Java 코드입니다/foo

불행히도이 결정을하기 전에 심볼릭 링크를 해결합니다.

따라서 응용 프로그램 빌드를 배포하고 설명 파일 이름 (예 : 릴리스 번호 또는 날짜)을 지정한다고 가정하십시오. 당신은 할 수없는 "진짜"이름을 가진 파일에 심볼릭 링크를 만들 - 당신은 하드 링크를 확인해야합니다.

foo.warfoo-20170129.war작동하지 않는 symlinked

foo.warfoo-20170129.war작동 하도록 연결되어 있습니다.

나는이 바람둥이 행동을 좋아하지 않지만, 하드 링크는 나에게 그 길을 알려줍니다.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.