diff --git a/src/uu/sort/src/sort.rs b/src/uu/sort/src/sort.rs index 4928dd17d39..5c97abba347 100644 --- a/src/uu/sort/src/sort.rs +++ b/src/uu/sort/src/sort.rs @@ -7,7 +7,7 @@ // https://pubs.opengroup.org/onlinepubs/9699919799/utilities/sort.html // https://www.gnu.org/software/coreutils/manual/html_node/sort-invocation.html -// spell-checker:ignore (misc) HFKJFK Mbdfhn getrlimit RLIMIT_NOFILE rlim bigdecimal extendedbigdecimal +// spell-checker:ignore (misc) HFKJFK Mbdfhn getrlimit RLIMIT_NOFILE rlim bigdecimal extendedbigdecimal hexdigit mod check; mod chunks; @@ -1834,15 +1834,27 @@ fn get_leading_gen(input: &str) -> Range { let mut had_e_notation = false; let mut had_decimal_pt = false; + let mut had_hex_notation: bool = false; while let Some((idx, c)) = char_indices.next() { + if had_hex_notation && c.is_ascii_hexdigit() { + continue; + } + if c.is_ascii_digit() { + if c == '0' && matches!(char_indices.peek(), Some((_, 'x' | 'X'))) { + had_hex_notation = true; + char_indices.next(); + } continue; } + if c == DECIMAL_PT && !had_decimal_pt && !had_e_notation { had_decimal_pt = true; continue; } - if (c == 'e' || c == 'E') && !had_e_notation { + let is_decimal_e = (c == 'e' || c == 'E') && !had_hex_notation; + let is_hex_e = (c == 'p' || c == 'P') && had_hex_notation; + if (is_decimal_e || is_hex_e) && !had_e_notation { // we can only consume the 'e' if what follow is either a digit, or a sign followed by a digit. if let Some(&(_, next_char)) = char_indices.peek() { if (next_char == '+' || next_char == '-') diff --git a/tests/by-util/test_sort.rs b/tests/by-util/test_sort.rs index 9a9022e2910..657a3addd5f 100644 --- a/tests/by-util/test_sort.rs +++ b/tests/by-util/test_sort.rs @@ -1556,3 +1556,15 @@ fn test_g_arbitrary() { .succeeds() .stdout_is(output); } + +#[test] +// Test hexadecimal numbers (and hex floats) +fn test_g_float_hex() { + let input = "0x123\n0x0\n0x2p10\n0x9p-10\n"; + let output = "0x0\n0x9p-10\n0x123\n0x2p10\n"; + new_ucmd!() + .args(&["-g"]) + .pipe_in(input) + .succeeds() + .stdout_is(output); +} diff --git a/tests/fixtures/sort/exponents_general.expected b/tests/fixtures/sort/exponents_general.expected index 308a82e1e34..0aa6e07514b 100644 --- a/tests/fixtures/sort/exponents_general.expected +++ b/tests/fixtures/sort/exponents_general.expected @@ -8,11 +8,11 @@ -12e-5555.5 0b10 // binary not supported -0x10 // hexadecimal not supported, but it should be 55e-20 55e-20.10 5.5.5.5 10E +0x10 64e+ 99e- 1000EDKLD diff --git a/tests/fixtures/sort/exponents_general.expected.debug b/tests/fixtures/sort/exponents_general.expected.debug index a7238d10e8c..657a3615949 100644 --- a/tests/fixtures/sort/exponents_general.expected.debug +++ b/tests/fixtures/sort/exponents_general.expected.debug @@ -28,9 +28,6 @@ ______________ 0b10 // binary not supported _ ____________________________ -0x10 // hexadecimal not supported, but it should be -_ -___________________________________________________ 55e-20 ______ ______ @@ -43,6 +40,9 @@ _______ 10E __ ___ +0x10 +____ +____ 64e+ __ ____ diff --git a/tests/fixtures/sort/exponents_general.txt b/tests/fixtures/sort/exponents_general.txt index 4a9bbba2e02..f6b88b8f5c3 100644 --- a/tests/fixtures/sort/exponents_general.txt +++ b/tests/fixtures/sort/exponents_general.txt @@ -4,7 +4,7 @@ +100000 10000K78 -0x10 // hexadecimal not supported, but it should be +0x10 10E 0b10 // binary not supported 64e+