Skip to content

Commit ef73c6b

Browse files
authored
Merge pull request #2098 from dscho/fix-parsing-of-legacy-git.git-commit
Fix parsing of legacy git.git commit
2 parents a149d4e + 191067e commit ef73c6b

File tree

7 files changed

+65
-11
lines changed

7 files changed

+65
-11
lines changed

gitoxide-core/src/index/information.rs

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -33,9 +33,6 @@ mod serde_only {
3333
}
3434
}
3535
}
36-
37-
#[derive(serde::Serialize, serde::Deserialize)]
38-
pub struct NodeId {}
3936
}
4037
}
4138

gix-object/src/commit/decode.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -44,14 +44,14 @@ pub fn commit<'a, E: ParserError<&'a [u8]> + AddContext<&'a [u8], StrContext>>(
4444
.context(StrContext::Expected("author <signature>".into())),
4545
(|i: &mut _| parse::header_field(i, b"committer", parse::signature))
4646
.context(StrContext::Expected("committer <signature>".into())),
47-
opt(|i: &mut _| parse::header_field(i, b"encoding", take_till(1.., NL)))
47+
opt(|i: &mut _| parse::header_field(i, b"encoding", take_till(0.., NL)))
4848
.context(StrContext::Expected("encoding <encoding>".into())),
4949
repeat(
5050
0..,
5151
alt((
5252
parse::any_header_field_multi_line.map(|(k, o)| (k.as_bstr(), Cow::Owned(o))),
5353
|i: &mut _| {
54-
parse::any_header_field(i, take_till(1.., NL))
54+
parse::any_header_field(i, take_till(0.., NL))
5555
.map(|(k, o)| (k.as_bstr(), Cow::Borrowed(o.as_bstr())))
5656
},
5757
)),

gix-object/src/commit/ref_iter.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -214,7 +214,7 @@ impl<'a> CommitRefIter<'a> {
214214
}
215215
}
216216
Encoding => {
217-
let encoding = opt(|i: &mut _| parse::header_field(i, b"encoding", take_till(1.., NL)))
217+
let encoding = opt(|i: &mut _| parse::header_field(i, b"encoding", take_till(0.., NL)))
218218
.context(StrContext::Expected("encoding <encoding>".into()))
219219
.parse_next(input)?;
220220
*state = State::ExtraHeaders;
@@ -227,7 +227,7 @@ impl<'a> CommitRefIter<'a> {
227227
let extra_header = opt(alt((
228228
|i: &mut _| parse::any_header_field_multi_line(i).map(|(k, o)| (k.as_bstr(), Cow::Owned(o))),
229229
|i: &mut _| {
230-
parse::any_header_field(i, take_till(1.., NL))
230+
parse::any_header_field(i, take_till(0.., NL))
231231
.map(|(k, o)| (k.as_bstr(), Cow::Borrowed(o.as_bstr())))
232232
},
233233
)))

gix-object/src/encode.rs

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,9 @@ pub(crate) fn header_field_multi_line(name: &[u8], value: &[u8], out: &mut dyn i
3838
let mut lines = value.as_bstr().lines_with_terminator();
3939
out.write_all(name)?;
4040
out.write_all(SPACE)?;
41-
out.write_all(lines.next().ok_or(Error::EmptyValue)?)?;
41+
if let Some(line) = lines.next() {
42+
out.write_all(line)?;
43+
}
4244
for line in lines {
4345
out.write_all(SPACE)?;
4446
out.write_all(line)?;

gix-object/src/parse.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ pub(crate) fn any_header_field_multi_line<'a, E: ParserError<&'a [u8]> + AddCont
1818
(
1919
terminated(take_till(1.., SPACE_OR_NL), SPACE),
2020
(
21-
take_till(1.., NL),
21+
take_till(0.., NL),
2222
NL,
2323
repeat(1.., terminated((SPACE, take_until(0.., NL)), NL)).map(|()| ()),
2424
)
Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
tree db079155794727ac821adfba2eb68b330cc0c120
2+
parent 33a11a20eb7610771268e34211509cbbdee76b1e
3+
author Junio C Hamano <[email protected]> 1319256362 -0700
4+
committer Junio C Hamano <[email protected]> 1319259176 -0700
5+
gpgsig -----BEGIN PGP SIGNATURE-----
6+
gpgsig Version: GnuPG v1.4.10 (GNU/Linux)
7+
gpgsig
8+
gpgsig iQIcBAABAgAGBQJOokwoAAoJELC16IaWr+bL0WoP/2QKYkWpEyXF608m2L/cB9Qx
9+
gpgsig /N0oBjyL1guIjPX9B3Wxq80dnLLEPnpnO39aiQIXFoJS0L6KEurqK6uDPHy3/ULa
10+
gpgsig QsAug2HeCLsDnIFbzFSpSIMv/bP/72FDb/idMBT99xTcQj5UJEUgj7AAtx0vnKvQ
11+
gpgsig pQIXtPu5GBUdhl3SiGgiJFRyp4r5EgV5I40GBwx/ty9cPEIN7ukJ3CR9+KC8eIGx
12+
gpgsig Az7qngi3dhTn7g+3Z8XX5OYFDMSt9xn1gxqWXOMNlG0mxCvpFe59kwciugp26KVp
13+
gpgsig n+yJ0UOdoxyZX8pdqXQjvklmoo7e55aaxtbHe7KSD56ebL7h7vHhkGWORU1dOp+h
14+
gpgsig Iv5dQItkKSR8afB7FmRjo8+B/2g0wZDKRTGhzm7d1gooO5gpXvuvm4GRl5Io+IEj
15+
gpgsig c7Li3EYmXADWUZWJtbDKDgKGKIOmWv72Qrz52iaESrhZ909HiXfn/jhHBuDRmLtQ
16+
gpgsig /4v3T4O25uhdZ4p/PjHQn/ZroCmDyMwmnrtw/tt5fSNrl4qGcYg8Jj/1ynfF1AtS
17+
gpgsig dM2LR65sOwXzSsqAbQjyRFYMLSWhHd/h8BcpZHDXmNBkZJVPm4zvD3ZVaAo6rtZD
18+
gpgsig WJ9YXWXtPhuf09OgYBzcBlamTrk9ByH+NCIdrFkqfhNF1YI5dArSZytIXJhpPI1e
19+
gpgsig TrmQAZf0BiI5J6PYN0AI
20+
gpgsig =Qg/+
21+
gpgsig -----END PGP SIGNATURE-----
22+
23+
pretty: %G[?GS] placeholders
24+
25+
Add new placeholders related to the GPG signature on signed commits.
26+
27+
- %GG to show the raw verification message from GPG;
28+
- %G? to show either "G" for Good, "B" for Bad;
29+
- %GS to show the name of the signer.
30+
31+
Signed-off-by: Junio C Hamano <[email protected]>

gix-object/tests/object/commit/from_bytes.rs

Lines changed: 26 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,10 @@
11
use gix_actor::SignatureRef;
2-
use gix_object::{bstr::ByteSlice, commit::message::body::TrailerRef, CommitRef};
2+
use gix_object::{bstr::ByteSlice, commit::message::body::TrailerRef, CommitRef, WriteTo};
33
use smallvec::SmallVec;
44

55
use crate::{
66
commit::{LONG_MESSAGE, MERGE_TAG, SIGNATURE},
7-
fixture_name, linus_signature, signature,
7+
fixture_name, hex_to_id, linus_signature, signature,
88
};
99

1010
#[test]
@@ -342,3 +342,27 @@ fn newline_right_after_signature_multiline_header() -> crate::Result {
342342
assert!(commit.message.starts_with(b"Rollup"));
343343
Ok(())
344344
}
345+
346+
#[test]
347+
fn bogus_multi_gpgsig_header() -> crate::Result {
348+
let fixture = fixture_name("commit", "bogus-gpgsig-lines-in-git.git.txt");
349+
let commit = CommitRef::from_bytes(&fixture)?;
350+
let pgp_sig = b"-----BEGIN PGP SIGNATURE-----".as_bstr();
351+
assert_eq!(commit.extra_headers().pgp_signature(), Some(pgp_sig));
352+
assert_eq!(
353+
commit.extra_headers().find_all("gpgsig").count(),
354+
17,
355+
"Each signature header line is prefixed with `gpgsig` here, so we parse it as extra header"
356+
);
357+
assert!(commit.message.starts_with(b"pretty: %G[?GS] placeholders"));
358+
359+
let mut buf = Vec::<u8>::new();
360+
commit.write_to(&mut buf)?;
361+
let actual = gix_object::compute_hash(gix_hash::Kind::Sha1, gix_object::Kind::Commit, &buf)?;
362+
assert_eq!(
363+
actual,
364+
hex_to_id("5f549aa2f78314ac37bbd436c8f80aea4c752e07"),
365+
"round-tripping works despite the strangeness"
366+
);
367+
Ok(())
368+
}

0 commit comments

Comments
 (0)