programing

서명된 Git 커밋을 확인하는 중입니까?

javamemo 2023. 8. 8. 19:58
반응형

서명된 Git 커밋을 확인하는 중입니까?

의 신최전과 사용gitPGP 키를 사용하여 태그 외에 개별 커밋에 서명할 수 있습니다.

git commit -m "some message" -S

이러한 그리다출이서표수있다습니시할명을러한력고에의음의 에 표시될 수.git log--show-signature옵션:

$ git log --show-signature
commit 93bd0a7529ef347f8dbca7efde43f7e99ab89515
gpg: Signature made Fri 28 Jun 2013 02:28:41 PM EDT using RSA key ID AC1964A8
gpg: Good signature from "Lars Kellogg-Stedman <lars@seas.harvard.edu>"
Author: Lars Kellogg-Stedman <lars@seas.harvard.edu>
Date:   Fri Jun 28 14:28:41 2013 -0400

    this is a test

그러나 특정 커밋에 대한 서명을 프로그래밍 방식으로 확인할 수 있는 방법이 있습니까?git log▁▁commit에 해당하는 커밋을 찾고 git tag -v지정된 커밋에 유효한 서명이 있었는지 여부를 나타내는 종료 코드를 제공하는 것입니다.

저처럼 검색 엔진을 통해 이 페이지로 오는 사람이 있을 경우: 질문이 게시된 이후 2년 동안 새로운 도구를 사용할 수 있게 되었습니다. 이가 있습니다.git verify-commit그리고.git verify-tag커밋과 태그를 각각 확인하는 데 사용할 수 있습니다.

참고: 최대 2.5g이며 사람이 읽을 수 있는 메시지만 표시됩니다.
검사를 자동화하려면 git 2.6+(2015년 3분기)에 다른 출력을 추가합니다.

commit 18443e, commit aff29d, commit ca194d5, commit 434060e, commit 8e98e5f, commit acc18f, commit d66aeff (2015년 6월 21일)를 brian m. Carlson()bk2204참조하십시오.
(Junio C Hamano에 의해 합병 -- -- commit ba12cb2, 2015년 8월 3일)

verify-tag/verify-commit gpg 합니다. gpg 파일을 참조하십시오.

verify-tag/verify-commit기본적으로 표준 오류 시 사람이 읽을 수 있는 출력을 표시합니다.
그러나 서명 정책을 자동으로 구현할 있도록 컴퓨터에서 읽을 수 있는 원시 gpg 상태 정보에 액세스하는 것도 유용할 있습니다.

만들 옵션 추가verify-tag사람이 읽을 수 있는 형식 대신 표준 오류에 대한 gpg 상태 정보를 생성합니다.

추가:

verify-tag서명은 양호하지만 키를 신뢰할 수 없는 경우 종료됩니다.verify-commit종료하지 못했습니다.
이러한 행동의 차이는 예상치 못한 것이고 원치 않는 것입니다.
때부터verify-tag했던 것처럼, 를 추가하여 실패한 테스트를 갖게 . 실패한 테스트를 추가합니다.verify-commit공유하다verify-tag의 행동


git 2.9 (2016년 6월) git 병합 문서 업데이트:

켈러 푹스('')의 커밋 05a5869(2016년 5월 13일)를 참조하십시오.
Help-by: 주니오 C 하마노().gitster
(주니오 C 하마노에 의해 합병 -- -- 2016년 5월 17일 커밋 be6ec 17에서)

--verify-signatures:
--no-verify-signatures:

병합할 사이드 분기의 팁 커밋이 유효한 키, 즉 유효한 udid를 가진 키로 서명되었는지 확인합니다. 기본 신뢰 모델에서는 서명 키가 신뢰할 수 있는
키로 서명되었음을 의미
합니다.
측면 분기의 커밋이 유효한 키로 서명되지 않으면 병합이 중단됩니다.


Git 2.10 업데이트(2016년 3분기)

리누스 토르발스()의 커밋 b624a3e(torvalds2016년 8월 16일)를 참조하십시오.
(주니오 C 하마노에 의해 합병 -- 83d9eb0, 2016년 8월 19일 커밋)

gpg-interface할 때 " 키 합니다.pgp signaturespgp 서 " 긴 " 키 " 형 합 " 선 호 니 을 " 다 력 출 " 식 할 때 인 " 을 명 확 " ▁format ▁key

"git log --show-signaturePGP 서명의 확인 상태를 표시하는 다른 명령은 32비트 key-id가 지난 세기이기 때문에 이제 더 긴 key-id를 표시합니다.

리누스의 원본은 과거에 고착된 바이너리 디스트리뷰터가 이전 코드베이스로 가져가기를 원할 경우를 대비하여 유지보수 트랙에 적용하도록 리베이스되었습니다.


Git 2.11+ (2016년 4분기)는 훨씬 더 정확할 것입니다.

Michael J Gruber()mjg의 커밋 661a180(2016년 10월 12일)을 참조하십시오.
(주니오 C 하마노에 의해 합병 -- 56d268b, 2016년 10월 26일 커밋)

인증 은 "GPG "에서할 수 있습니다.%G?만료된 키로 만든 서명, 해지된 키로 만든 서명 등을 구분할 수 있을 정도로 예쁜 형식 지정자가 풍부하지 않습니다.
새 출력 문자가 지정되어 해당 문자를 표현합니다.

gpg2에 따름:

각 서 에 대 코 중 하 나 만 드 해 명 만GOODSIG,BADSIG,EXPSIG,EXPKEYSIG,REVKEYSIG또는ERRSIG방출됩니다.

이제 설명서에는 다음이 포함됩니다.

  • '%G?
  • "G 서명을 , ,,위▁a해▁for좋서▁(은▁(명.
  • "B서명을 , 쁜명서때문에나에▁for.
  • "U알 수 , 효성을알유수위서해을명,
  • "X유효기간이,
  • "Y이 지난키에 , 료된키에만의만위좋해서명을은들진어해,▁made,,
  • "R키로 , 소된키에취의만위좋해서명을은,
  • "E할 수 키 "키 분실" 및 "키 분실"(키: 키 분실)"N 없이

2 "Git 2.12 (2017년 1분기)"git tag그리고 "git verify-tagGPG 검증 상태를 --format=<placeholders>"" 출력 형식으로 입력하는 방법을 배웠습니다.

commit 4fea72f, commit 02c5433, commit ff3c8c8(2017년 1월 17일)을 산티아고 토레스()SantiagoTorres가 참조.
커밋 07d347c, 커밋 2111a7, 커밋 94240b9(2017년 1월 17일) 참조.
(주니오 C 하마노에 의해 합병 -- -- 237bdd9, 2017년 1월 31일 커밋)

추가하기--formatgit tag -vGPG 확인의 기본 출력을 음소거하고 대신 포맷된 태그 개체를 인쇄합니다.
이를 통해 발신자는 GPG 확인 시 refs/tag의 태그 이름과 태그 개체 헤더의 태그 이름을 교차 확인할 수 있습니다.


2은 Git 2.16(2018년 1분기)과 자동화될 입니다.merge.verifySignatures구성 변수입니다.

commit 7f8ca20, commit ca779e8 (2017년 12월 10일) by Hans Jerry Illikainen ('') 참조.
(주니오 C 하마노에 의해 합병되었습니다 -- -- 커밋 0433d53, 2017년 12월 28일)

mergeverifySignatures

git merge --verify-signatures병합할 분기의 팁 커밋이 제대로 서명되었는지 확인하는 데 사용할 수 있지만 매번 이를 지정해야 하는 번거로움이 있습니다.

기본적으로 이 동작을 사용하도록 설정하는 구성 옵션을 추가합니다. 이 동작은 다음에서 재정의할 수 있습니다.--no-verify-signatures.

이제 구성 관리자 페이지에 다음이 표시됩니다.

merge.verifySignatures:

만약 사실이라면, 이것은 다음과 같습니다.--verify-signatures명령줄 옵션.


Git 2.19 (2018년 3분기)가 훨씬 더 도움이 됩니다. "git verify-tag그리고 "git verify-commit기본 "의 종료 상태를 사용하도록 교육받았습니다.gpg --verify잘못되었거나 신뢰할 수 없는 서명을 발견했습니다.

참고: Git 2.19에서는 "" 또는 x509""로 openpgp설정할 수 있으며, 포맷을 처리하기 위해 사용할 프로그램을 지정하는 데 사용됨) 사용하여 ""gnupg 대신 ""gpgsm를 통해 CMS와의 x.509 인증서를 사용할 수 있습니다.

주니오 C 하마노()gitster의 커밋 4e5dc9c(2018년 8월 9일)를 참조하십시오.
지원자: Vojtech Myslivec(),VojtechMyslivec 브라이언 칼슨(),bk2204 제프 peff킹().
(주니오 C 하마노에 의해 합병되었습니다 -- -- 2018년 8월 20일 커밋 4d34122에서)

gpg-interface종료 상태 전파gpg방문자들에게 돌아가는

2015년 중반 gpg-interface API가 v2.6.0-rc0~114 정도에서 서명된 태그 및 서명된 커밋에 대한 서명 확인 코드 경로 지원을 통합했을 때, 우리는 실수로 GPG 서명 검증을 느슨하게 했습니다.

그 변경 전에 서명된 커밋은 "를 검색하여 확인되었습니다.G"GPG의 우드 서명, 종료 상태는 무시"gpg --verify프로세스, 서명된 태그는 단순히 종료 상태를 전달하여 확인되었습니다."gpg --verify관통하여

현재 보유하고 있는 통합 코드는 "의 종료 상태를 무시합니다.gpg --verify서명이 만료되지 않은 키와 일치할 때 키에 대한 신뢰 관계에 관계없이 성공적인 확인을 반환합니다.G"좋은 것들, 우리는 받아들입니다"U"신뢰할 수 없는 항목).

이 명령어들이 "밑에 있을 때 종료 상태와 함께 실패 신호를 보내도록 합니다.gpg --verify(또는 "에 의해 지정된 사용자 지정 명령)gpg.program구성 변수)를 사용합니다.
따라서 신뢰할 수 없는 키로 만들어진 서명이 올바르게 확인되더라도 이를 거부하는 역호환적인 방식으로 동작이 변경됩니다.gpg --verify행동합니다.

코드는 여전히 "에서 얻은 0 종료 상태를 재정의합니다.gpg(또는)gpg.program) 출력에 서명이 양호하지 않거나 정확하게 계산되지 않지만 신뢰할 수 없는 키로 만들어진 경우, "주변에 제대로 작성되지 않은 래퍼를 잡습니다.gpg사용자가 우리에게 줄 수 있습니다.

"는 제외할 수 있습니다.U"이 폴백 코드에서 신뢰할 수 없는 지원을 제공하지만, 이는 단일 커밋에서 두 가지 역호환성이 없는 변경을 수행하는 것이므로 현재로서는 이 문제를 피하도록 하겠습니다.
원하는 경우 후속 변경을 수행할 수 있습니다.


암호화를 수행하기 전에 키를 신뢰/서명해야 합니다.

신뢰 측면에서는 다음과 같은 진전이 있습니다.
Git 2.26(2020년 1분기)과 함께,gpg.minTrustLevel다양한 서명 확인 코드 경로에 필요한 최소 신뢰 수준을 알려주는 구성 변수가 도입되었습니다.

한스 제리 일리카이넨()illikainen의 커밋 54887b4(2019년 12월 27일)를 참조하십시오.
(주니오 C 하마노에 의해 합병 -- -- 2020년 1월 30일 11ad30b 커밋에서)

minTrustLevel을 구성 옵션으로 gpg-interface추가

사인 오프 바이: 한스 제리 일리카이넨

이전에는 병합 및 꺼내기 작업에 대한 서명 확인에서 키의 신뢰 수준이 다음 중 하나인지 확인했습니다.TRUST_NEVER또는TRUST_UNDEFINEDverify_merge_signature().

만약 그렇다면, 그 과정은die()'d.

서명 확인을 수행한 다른 코드 경로는 전적으로 다음의 반환 코드에 의존했습니다.check_commit_signature().

그리고 신뢰 수준과 상관없이 좋은 키로 만들어진 서명은 유효한 것으로 간주되었습니다.check_commit_signature().

이러한 동작의 차이로 인해 사용자는 링에 있는 키의 신뢰 수준이 항상 Git에 의해 고려된다고 잘못 가정할 수 있습니다(예: 또는 ).

작동 방식은 키/시그니처 상태의 결과와 가장 낮은 2개의 신뢰 수준을 저장하는 것이었습니다.result의 일원signature_check구조(이 상태 행 중 마지막으로 발생한 행이 기록됨)result).

이들은 하위 섹션의 GPG에 문서화되어 있습니다.General status codes그리고.Key related,각각 다음과 같다.

GPG 설명서에는 코드에 대해 다음과 같이 나와 있습니다.


다음은 몇 가지 유사한 상태 코드입니다.

- TRUST_UNDEFINED <error_token>
- TRUST_NEVER     <error_token>
- TRUST_MARGINAL  [0  [<validation_model>]]
- TRUST_FULLY     [0  [<validation_model>]]
- TRUST_ULTIMATE  [0  [<validation_model>]]

양호한 서명의 경우 서명을 만드는 데 사용된 키의 유효성을 나타내기 위해 이러한 상태 줄 중 하나가 방출됩니다.
오류 토큰 값은 현재 gpgsm에서만 출력됩니다.


신뢰 수준이 키 및/또는 서명의 유효성과 개념적으로 다르다는 것이 제 해석입니다.

그것은 또한 오래된 코드의 가정이었던 것 같습니다.check_signature()의 결과로G(의 경우와 같이)GOODSIG) 및 'U(의 경우와 같이)TRUST_NEVER또는TRUST_UNDEFINED)둘 다 성공한 것으로 간주되었습니다.

의 결과인 두 가지 경우U에 특별한 의미가 있었습니다.verify_merge_signature()(이로 인해 발생한 경우git로.die()) 및 인format_commit_one()(그것이 출력에 영향을 미쳤던 곳.%G?형식 지정자).

제 생각에 그것의 처리를 재요인화하는 것이 타당하다고 생각합니다.TRUST_ status사용자가 개별적인 부분이 아닌 전체적으로 적용되는 최소 신뢰 수준을 구성할 수 있는 라인git(예: 병합) 직접 수행합니다(이전 버전과의 호환성이 있는 유예 기간 제외).

또한 신뢰 수준을 키/서명 상태와 동일한 구조 구성원에 저장하지 않는 것이 타당하다고 생각합니다.

의 존재가 있는 동안.TRUST_ status코드는 서명이 양호함을 의미합니다(위에 포함된 스니펫의 첫 번째 단락 참조). 내가 말할 수 있는 한 GPG의 상태 줄 순서는 잘 정의되지 않았습니다. 따라서 신뢰 수준이 동일한 멤버에 저장되면 키/서명 상태로 덮어쓸 수 있을 것으로 보입니다.signature_check구조.

이 패치는 새 구성 옵션을 도입합니다.

신뢰 수준 검증을 에 통합하고 새로운 기능을 추가합니다.trust_level의 회원.signature_check구조.

하위 호환성은 다음에서 특별한 경우를 도입하여 유지됩니다.verify_merge_signature()사용자가 설정할 수 없는 경우에는gpg.minTrustLevel설정된 다음, 거부하는 기존 동작TRUST_UNDEFINED그리고.TRUST_NEVER적용됩니다.

반면에, 만약에,gpg.minTrustLevel이 설정되면 해당 값이 이전 동작을 재정의합니다.

마찬가지로,%G?형식 지정자가 계속 표시됩니다. 'U신뢰 수준이 다음과 같은 키로 작성된 서명의 경우TRUST_UNDEFINED또는TRUST_NEVER,'라고 해도U문자가 더 이상 존재하지 않습니다.result의 일원signature_check구조.

새 형식 지정자,%GT또한 서명에 대해 가능한 모든 신뢰 수준을 표시하려는 사용자를 위해 도입되었습니다.

또 다른 접근 방식은 단순히 신뢰 수준 요구사항을 삭제하는 것이었습니다.verify_merge_signature().

이렇게 하면 서명 확인을 수행하는 git의 다른 부분과 동작이 일치할 수 있습니다.

그러나 서명 키에 대한 최소 신뢰 수준을 요구하는 것은 실제 사용 사례가 있는 것 같습니다.

예를 들어 Qubes OS 프로젝트에서 사용하는 빌드 시스템은 현재 verify-tag의 원시 출력을 구문 분석하여 git 태그 서명에 사용되는 키에 대한 최소 신뢰 수준을 주장합니다.

이제 man 페이지에는 다음이 포함됩니다.

gpg.minTrustLevel:

서명 확인을 위한 최소 신뢰 수준을 지정합니다.
이 옵션이 설정되지 않은 경우 병합 작업에 대한 서명 확인에는 최소 키가 필요합니다.marginal신뢰.
서명 확인을 수행하는 다른 작업에는 적어도 다음이 포함된 키가 필요합니다.undefined신뢰.
이 옵션을 설정하면 모든 작업에 필요한 신뢰 수준이 재정의됩니다.중요도가 높은 순서대로 지원되는 값:

  • undefined
  • never
  • marginal
  • fully
  • ultimate

Git 2.26(2020년 1분기)과 함께, "git show오류 출력에 원시 형식으로 개체 이름을 지정한 경우도 있습니다. 오류 출력은 16진수로 지정하도록 수정되었습니다.

show_one_mergetag: 부모가 아닌 것을 16진수 형식으로 인쇄합니다.

병합 태그가 얕은 복제본 다음에 발생할 수 있는 부모가 아닌 이름을 지정할 때 해당 해시는 이전에 원시 데이터로 인쇄되었습니다.
대신 16진수 형식으로 인쇄합니다.

테스트 대상git -C shallow log --graph --show-signature -n1 plain-shallow잠시 후에git clone --depth 1 --no-local . shallow


Git 2.27(2020년 2분기)을 통해 GnuPG와 인터페이스할 코드가 리팩터링되었습니다.

한스 제리 일리카이넨()illikainen의 commit 6794898, commit f1e3df3(2020년 3월 4일)를 참조하십시오.
(주니오 C 하마노에 의해 합병 -- -- 커밋 fa82be9, 2020년 3월 27일)

gpg-interface선호하는check_signature()GPG 확인용

사인 오프 바이: 한스 제리 일리카이넨

이 커밋은 다음의 사용을 반영합니다.verify_signed_buffer()사용할 수 없는check_signature()대신.

또한 회전합니다.verify_signed_buffer()파일-로컬 함수로 전환합니다. 이제 내부적으로만 호출되기 때문입니다.check_signature().

이전에는 Git의 다른 부분에서 GPG 서명 검증을 수행하기 위해 두 개의 글로벌 범위 기능이 사용되었습니다.verify_signed_buffer()그리고.check_signature().

지금만check_signature()사용됩니다.

verify_signed_buffer()Michau Górny가 설명한 것처럼 중복 서명을 방지하지 않습니다.

대신 GPG로부터의 비오류 종료 코드와 적어도 하나의 존재만 보장합니다.GOODSIG상태 필드.

이것은 와 대조적입니다.check_signature()둘 이상의 서명이 발견되면 오류를 반환합니다.

낮은 수준의 검증은 다음을 사용합니다.verify_signed_buffer()발신자가 GPG 상태 메시지의 다양한 부분을 직접 구문 분석하고 검증하지 않으면 문제가 발생합니다.

그리고 이러한 메시지를 처리하는 것은 기능과 함께 예약되어야 하는 작업처럼 보입니다.check_signature().

게다가, 의 사용.verify_signed_buffer()GPG 상태 줄의 내용에 의존하는 새로운 기능을 도입하는 것을 어렵게 합니다.

이제 서명 확인을 수행하는 모든 작업은 에 단일 진입점을 공유합니다.

이를 통해 GPG 서명 검증에서 변경된 기능이나 추가 기능을 Git의 모든 부분에 전파하는 것이 더 쉬워집니다. 동일한 정도의 검증을 수행하지 않는 홀수 에지 케이스가 없습니다.


Git 2.31 (Q1 2021)에서는 서명된 커밋과 태그를 통해 두 개체 이름(SHA-1에 하나, SHA-256에 하나)이 모두 서명된 개체를 확인할 수 있습니다.

커밋 9b27b49,bk2204 커밋 88bce0e, 커밋 937032e, 커밋 482c119(2021년 2월 11일), 커밋 1fb5cf0, 커밋 83dff3e(2021년 1월 18일)를 브라이언 칼슨()이 참조하십시오.
(주니오 C 하마노에 의해 합병 -- -- 2021년 2월 22일 커밋 15af6e6에서)

commit서명된 커밋을 구문 분석할 때 추가 서명 무시

사인 오프 바이: 브라이언 칼슨.

여러 서명을 사용하여 커밋을 만들 때 두 서명 모두 다른 서명을 포함하지 않습니다.
따라서 커밋을 확인할 수 있도록 서명된 페이로드를 생성할 때 다른 서명을 제거해야 합니다. 그렇지 않으면 서명된 것과 페이로드가 다릅니다.
그렇게 하고, 여러 알고리즘으로 검증할 준비를 하기 위해, 우리가 검증하고자 하는 알고리즘을 전달합니다.parse_signed_commit.


Brandon은 댓글에서 제안합니다.git log별칭, 주요 상태를 표시합니다.

[alias]
    lg = "!f() { \
        git log --all --color --graph --pretty=format:'%C(bold yellow)<sig>%G?</sig>%C(reset) %C(red)%h%C(reset) -%C(yellow)%d%C(reset) %s %C(green)(%cr) %C(blue)<%an>%C(reset)' | \
        sed \
        -e 's#<sig>G</sig>#Good#' \
        -e 's#<sig>B</sig>#\\nBAD \\nBAD \\nBAD \\nBAD \\nBAD#' \
        -e 's#<sig>U</sig>#Unknown#' \
        -e 's#<sig>X</sig>#Expired#' \
        -e 's#<sig>Y</sig>#Expired Key#' \
        -e 's#<sig>R</sig>#Revoked#' \
        -e 's#<sig>E</sig>#Missing Key#' \
        -e 's#<sig>N</sig>#None#' | \
        less -r; \
    }; f"

코드를 대충 검사한 결과 그러한 직접적인 방법은 없는 것으로 나타났습니다.

Git 소스의 모든 테스트는 다음에 의존합니다.grep의 출력에 pinggit show(set/t7510-signed-commit 참조).sh)를 입력합니다.

다음과 같은 방법을 사용하여 출력을 사용자 지정할 수 있습니다.--pretty "%H %G?%"쉽게 분석할 수 있습니다.

당신이 물어볼 수 있는 것 같습니다.git merge서명을 확인하기 위해 다시 말하지만, 그 테스트는 다음에 의존합니다.grep(t/t7612-merge-verify-signatures.sh 참조).잘못된 서명이 원인이 될 것 같습니다.git merge잘못된 서명을 사용하여 종료하기 때문에 오늘 어딘가에서 테스트 병합을 수행하고 병합을 폐기함으로써 잠재적으로 이 문제를 해킹할 수 있지만, 그것은 단순히 grep를 부르는 것보다 더 나빠 보입니다.

언급URL : https://stackoverflow.com/questions/17371955/verifying-signed-git-commits

반응형