This commit is contained in:
sylvestre
2022-10-08 03:43:05 +00:00
parent 358b993717
commit 5c112c798c
29 changed files with 599 additions and 631 deletions
+1 -1
View File
File diff suppressed because one or more lines are too long
+1 -1
View File
@@ -112,7 +112,7 @@ var sourcesIndex = JSON.parse('{\
"uu_chroot":["",[],["chroot.rs","error.rs"]],\
"uu_cksum":["",[],["cksum.rs"]],\
"uu_comm":["",[],["comm.rs"]],\
"uu_cp":["",[],["cp.rs"]],\
"uu_cp":["",[["platform",[],["linux.rs","mod.rs"]]],["cp.rs"]],\
"uu_csplit":["",[],["csplit.rs","csplit_error.rs","patterns.rs","split_name.rs"]],\
"uu_cut":["",[],["cut.rs","searcher.rs"]],\
"uu_date":["",[],["date.rs"]],\
+4 -412
View File
@@ -1684,210 +1684,6 @@
<span id="1684">1684</span>
<span id="1685">1685</span>
<span id="1686">1686</span>
<span id="1687">1687</span>
<span id="1688">1688</span>
<span id="1689">1689</span>
<span id="1690">1690</span>
<span id="1691">1691</span>
<span id="1692">1692</span>
<span id="1693">1693</span>
<span id="1694">1694</span>
<span id="1695">1695</span>
<span id="1696">1696</span>
<span id="1697">1697</span>
<span id="1698">1698</span>
<span id="1699">1699</span>
<span id="1700">1700</span>
<span id="1701">1701</span>
<span id="1702">1702</span>
<span id="1703">1703</span>
<span id="1704">1704</span>
<span id="1705">1705</span>
<span id="1706">1706</span>
<span id="1707">1707</span>
<span id="1708">1708</span>
<span id="1709">1709</span>
<span id="1710">1710</span>
<span id="1711">1711</span>
<span id="1712">1712</span>
<span id="1713">1713</span>
<span id="1714">1714</span>
<span id="1715">1715</span>
<span id="1716">1716</span>
<span id="1717">1717</span>
<span id="1718">1718</span>
<span id="1719">1719</span>
<span id="1720">1720</span>
<span id="1721">1721</span>
<span id="1722">1722</span>
<span id="1723">1723</span>
<span id="1724">1724</span>
<span id="1725">1725</span>
<span id="1726">1726</span>
<span id="1727">1727</span>
<span id="1728">1728</span>
<span id="1729">1729</span>
<span id="1730">1730</span>
<span id="1731">1731</span>
<span id="1732">1732</span>
<span id="1733">1733</span>
<span id="1734">1734</span>
<span id="1735">1735</span>
<span id="1736">1736</span>
<span id="1737">1737</span>
<span id="1738">1738</span>
<span id="1739">1739</span>
<span id="1740">1740</span>
<span id="1741">1741</span>
<span id="1742">1742</span>
<span id="1743">1743</span>
<span id="1744">1744</span>
<span id="1745">1745</span>
<span id="1746">1746</span>
<span id="1747">1747</span>
<span id="1748">1748</span>
<span id="1749">1749</span>
<span id="1750">1750</span>
<span id="1751">1751</span>
<span id="1752">1752</span>
<span id="1753">1753</span>
<span id="1754">1754</span>
<span id="1755">1755</span>
<span id="1756">1756</span>
<span id="1757">1757</span>
<span id="1758">1758</span>
<span id="1759">1759</span>
<span id="1760">1760</span>
<span id="1761">1761</span>
<span id="1762">1762</span>
<span id="1763">1763</span>
<span id="1764">1764</span>
<span id="1765">1765</span>
<span id="1766">1766</span>
<span id="1767">1767</span>
<span id="1768">1768</span>
<span id="1769">1769</span>
<span id="1770">1770</span>
<span id="1771">1771</span>
<span id="1772">1772</span>
<span id="1773">1773</span>
<span id="1774">1774</span>
<span id="1775">1775</span>
<span id="1776">1776</span>
<span id="1777">1777</span>
<span id="1778">1778</span>
<span id="1779">1779</span>
<span id="1780">1780</span>
<span id="1781">1781</span>
<span id="1782">1782</span>
<span id="1783">1783</span>
<span id="1784">1784</span>
<span id="1785">1785</span>
<span id="1786">1786</span>
<span id="1787">1787</span>
<span id="1788">1788</span>
<span id="1789">1789</span>
<span id="1790">1790</span>
<span id="1791">1791</span>
<span id="1792">1792</span>
<span id="1793">1793</span>
<span id="1794">1794</span>
<span id="1795">1795</span>
<span id="1796">1796</span>
<span id="1797">1797</span>
<span id="1798">1798</span>
<span id="1799">1799</span>
<span id="1800">1800</span>
<span id="1801">1801</span>
<span id="1802">1802</span>
<span id="1803">1803</span>
<span id="1804">1804</span>
<span id="1805">1805</span>
<span id="1806">1806</span>
<span id="1807">1807</span>
<span id="1808">1808</span>
<span id="1809">1809</span>
<span id="1810">1810</span>
<span id="1811">1811</span>
<span id="1812">1812</span>
<span id="1813">1813</span>
<span id="1814">1814</span>
<span id="1815">1815</span>
<span id="1816">1816</span>
<span id="1817">1817</span>
<span id="1818">1818</span>
<span id="1819">1819</span>
<span id="1820">1820</span>
<span id="1821">1821</span>
<span id="1822">1822</span>
<span id="1823">1823</span>
<span id="1824">1824</span>
<span id="1825">1825</span>
<span id="1826">1826</span>
<span id="1827">1827</span>
<span id="1828">1828</span>
<span id="1829">1829</span>
<span id="1830">1830</span>
<span id="1831">1831</span>
<span id="1832">1832</span>
<span id="1833">1833</span>
<span id="1834">1834</span>
<span id="1835">1835</span>
<span id="1836">1836</span>
<span id="1837">1837</span>
<span id="1838">1838</span>
<span id="1839">1839</span>
<span id="1840">1840</span>
<span id="1841">1841</span>
<span id="1842">1842</span>
<span id="1843">1843</span>
<span id="1844">1844</span>
<span id="1845">1845</span>
<span id="1846">1846</span>
<span id="1847">1847</span>
<span id="1848">1848</span>
<span id="1849">1849</span>
<span id="1850">1850</span>
<span id="1851">1851</span>
<span id="1852">1852</span>
<span id="1853">1853</span>
<span id="1854">1854</span>
<span id="1855">1855</span>
<span id="1856">1856</span>
<span id="1857">1857</span>
<span id="1858">1858</span>
<span id="1859">1859</span>
<span id="1860">1860</span>
<span id="1861">1861</span>
<span id="1862">1862</span>
<span id="1863">1863</span>
<span id="1864">1864</span>
<span id="1865">1865</span>
<span id="1866">1866</span>
<span id="1867">1867</span>
<span id="1868">1868</span>
<span id="1869">1869</span>
<span id="1870">1870</span>
<span id="1871">1871</span>
<span id="1872">1872</span>
<span id="1873">1873</span>
<span id="1874">1874</span>
<span id="1875">1875</span>
<span id="1876">1876</span>
<span id="1877">1877</span>
<span id="1878">1878</span>
<span id="1879">1879</span>
<span id="1880">1880</span>
<span id="1881">1881</span>
<span id="1882">1882</span>
<span id="1883">1883</span>
<span id="1884">1884</span>
<span id="1885">1885</span>
<span id="1886">1886</span>
<span id="1887">1887</span>
<span id="1888">1888</span>
<span id="1889">1889</span>
<span id="1890">1890</span>
</pre><pre class="rust"><code><span class="attribute">#![<span class="ident">allow</span>(<span class="ident">clippy::missing_safety_doc</span>)]</span>
<span class="attribute">#![<span class="ident">allow</span>(<span class="ident">clippy::extra_unused_lifetimes</span>)]</span>
@@ -1912,15 +1708,11 @@
<span class="attribute">#[<span class="ident">cfg</span>(<span class="ident">not</span>(<span class="ident">windows</span>))]</span>
<span class="kw">use</span> <span class="ident">std::ffi::CString</span>;
<span class="kw">use</span> <span class="ident">std::fs</span>::{<span class="self">self</span>, <span class="ident">File</span>, <span class="ident">OpenOptions</span>};
<span class="attribute">#[<span class="ident">cfg</span>(<span class="ident">any</span>(<span class="ident">target_os</span> <span class="op">=</span> <span class="string">&quot;linux&quot;</span>, <span class="ident">target_os</span> <span class="op">=</span> <span class="string">&quot;android&quot;</span>))]</span>
<span class="kw">use</span> <span class="ident">std::io::Read</span>;
<span class="kw">use</span> <span class="ident">std::io</span>::{<span class="self">self</span>, <span class="ident">stderr</span>, <span class="ident">stdin</span>, <span class="ident">Write</span>};
<span class="attribute">#[<span class="ident">cfg</span>(<span class="ident">unix</span>)]</span>
<span class="kw">use</span> <span class="ident">std::os::unix::ffi::OsStrExt</span>;
<span class="attribute">#[<span class="ident">cfg</span>(<span class="ident">unix</span>)]</span>
<span class="kw">use</span> <span class="ident">std::os::unix::fs</span>::{<span class="ident">FileTypeExt</span>, <span class="ident">PermissionsExt</span>};
<span class="attribute">#[<span class="ident">cfg</span>(<span class="ident">any</span>(<span class="ident">target_os</span> <span class="op">=</span> <span class="string">&quot;linux&quot;</span>, <span class="ident">target_os</span> <span class="op">=</span> <span class="string">&quot;android&quot;</span>))]</span>
<span class="kw">use</span> <span class="ident">std::os::unix::io::AsRawFd</span>;
<span class="kw">use</span> <span class="ident">std::path</span>::{<span class="ident">Path</span>, <span class="ident">PathBuf</span>, <span class="ident">StripPrefixError</span>};
<span class="kw">use</span> <span class="ident">std::str::FromStr</span>;
<span class="kw">use</span> <span class="ident">std::string::ToString</span>;
@@ -1939,6 +1731,9 @@
};
<span class="kw">use</span> <span class="ident">walkdir::WalkDir</span>;
<span class="kw">mod</span> <span class="ident">platform</span>;
<span class="kw">use</span> <span class="ident">platform::copy_on_write</span>;
<span class="macro">quick_error!</span> {
<span class="attribute">#[<span class="ident">derive</span>(<span class="ident">Debug</span>)]</span>
<span class="kw">pub</span> <span class="kw">enum</span> <span class="ident">Error</span> {
@@ -2114,16 +1909,6 @@
<span class="ident">verbose</span>: <span class="ident">bool</span>,
}
<span class="comment">// From /usr/include/linux/fs.h:</span>
<span class="comment">// #define FICLONE _IOW(0x94, 9, int)</span>
<span class="attribute">#[<span class="ident">cfg</span>(<span class="ident">any</span>(<span class="ident">target_os</span> <span class="op">=</span> <span class="string">&quot;linux&quot;</span>, <span class="ident">target_os</span> <span class="op">=</span> <span class="string">&quot;android&quot;</span>))]</span>
<span class="comment">// Use a macro as libc::ioctl expects u32 or u64 depending on the arch</span>
<span class="macro">macro_rules!</span> <span class="ident">FICLONE</span> {
() =&gt; {
<span class="number">0x40049409</span>
};
}
<span class="kw">static</span> <span class="ident">ABOUT</span>: <span class="kw-2">&amp;</span><span class="ident">str</span> <span class="op">=</span> <span class="string">&quot;Copy SOURCE to DEST, or multiple SOURCE(s) to DIRECTORY.&quot;</span>;
<span class="kw">static</span> <span class="ident">LONG_HELP</span>: <span class="kw-2">&amp;</span><span class="ident">str</span> <span class="op">=</span> <span class="string">&quot;&quot;</span>;
<span class="kw">static</span> <span class="ident">EXIT_ERR</span>: <span class="ident">i32</span> <span class="op">=</span> <span class="number">1</span>;
@@ -3479,26 +3264,7 @@
} <span class="kw">else</span> <span class="kw">if</span> <span class="ident">source_is_symlink</span> {
<span class="ident">copy_link</span>(<span class="ident">source</span>, <span class="ident">dest</span>, <span class="ident">symlinked_files</span>)<span class="question-mark">?</span>;
} <span class="kw">else</span> {
<span class="attribute">#[<span class="ident">cfg</span>(<span class="ident">target_os</span> <span class="op">=</span> <span class="string">&quot;macos&quot;</span>)]</span>
<span class="ident">copy_on_write_macos</span>(
<span class="ident">source</span>,
<span class="ident">dest</span>,
<span class="ident">options</span>.<span class="ident">reflink_mode</span>,
<span class="ident">options</span>.<span class="ident">sparse_mode</span>,
<span class="ident">context</span>,
)<span class="question-mark">?</span>;
<span class="attribute">#[<span class="ident">cfg</span>(<span class="ident">any</span>(<span class="ident">target_os</span> <span class="op">=</span> <span class="string">&quot;linux&quot;</span>, <span class="ident">target_os</span> <span class="op">=</span> <span class="string">&quot;android&quot;</span>))]</span>
<span class="ident">copy_on_write_linux</span>(
<span class="ident">source</span>,
<span class="ident">dest</span>,
<span class="ident">options</span>.<span class="ident">reflink_mode</span>,
<span class="ident">options</span>.<span class="ident">sparse_mode</span>,
<span class="ident">context</span>,
)<span class="question-mark">?</span>;
<span class="attribute">#[<span class="ident">cfg</span>(<span class="ident">not</span>(<span class="ident">any</span>(<span class="ident">target_os</span> <span class="op">=</span> <span class="string">&quot;linux&quot;</span>, <span class="ident">target_os</span> <span class="op">=</span> <span class="string">&quot;android&quot;</span>, <span class="ident">target_os</span> <span class="op">=</span> <span class="string">&quot;macos&quot;</span>)))]</span>
<span class="ident">copy_no_cow_fallback</span>(
<span class="ident">copy_on_write</span>(
<span class="ident">source</span>,
<span class="ident">dest</span>,
<span class="ident">options</span>.<span class="ident">reflink_mode</span>,
@@ -3554,180 +3320,6 @@
<span class="ident">symlink_file</span>(<span class="kw-2">&amp;</span><span class="ident">link</span>, <span class="kw-2">&amp;</span><span class="ident">dest</span>, <span class="kw-2">&amp;</span><span class="ident">context_for</span>(<span class="kw-2">&amp;</span><span class="ident">link</span>, <span class="kw-2">&amp;</span><span class="ident">dest</span>), <span class="ident">symlinked_files</span>)
}
<span class="doccomment">/// Copies `source` to `dest` for systems without copy-on-write</span>
<span class="attribute">#[<span class="ident">cfg</span>(<span class="ident">not</span>(<span class="ident">any</span>(<span class="ident">target_os</span> <span class="op">=</span> <span class="string">&quot;linux&quot;</span>, <span class="ident">target_os</span> <span class="op">=</span> <span class="string">&quot;android&quot;</span>, <span class="ident">target_os</span> <span class="op">=</span> <span class="string">&quot;macos&quot;</span>)))]</span>
<span class="kw">fn</span> <span class="ident">copy_no_cow_fallback</span>(
<span class="ident">source</span>: <span class="kw-2">&amp;</span><span class="ident">Path</span>,
<span class="ident">dest</span>: <span class="kw-2">&amp;</span><span class="ident">Path</span>,
<span class="ident">reflink_mode</span>: <span class="ident">ReflinkMode</span>,
<span class="ident">sparse_mode</span>: <span class="ident">SparseMode</span>,
<span class="ident">context</span>: <span class="kw-2">&amp;</span><span class="ident">str</span>,
) -&gt; <span class="ident">CopyResult</span><span class="op">&lt;</span>()<span class="op">&gt;</span> {
<span class="kw">if</span> <span class="ident">reflink_mode</span> <span class="op">!</span><span class="op">=</span> <span class="ident">ReflinkMode::Never</span> {
<span class="kw">return</span> <span class="prelude-val">Err</span>(<span class="string">&quot;--reflink is only supported on linux and macOS&quot;</span>
.<span class="ident">to_string</span>()
.<span class="ident">into</span>());
}
<span class="kw">if</span> <span class="ident">sparse_mode</span> <span class="op">!</span><span class="op">=</span> <span class="ident">SparseMode::Auto</span> {
<span class="kw">return</span> <span class="prelude-val">Err</span>(<span class="string">&quot;--sparse is only supported on linux&quot;</span>.<span class="ident">to_string</span>().<span class="ident">into</span>());
}
<span class="ident">fs::copy</span>(<span class="ident">source</span>, <span class="ident">dest</span>).<span class="ident">context</span>(<span class="ident">context</span>)<span class="question-mark">?</span>;
<span class="prelude-val">Ok</span>(())
}
<span class="doccomment">/// Use the Linux `ioctl_ficlone` API to do a copy-on-write clone.</span>
<span class="doccomment">///</span>
<span class="doccomment">/// If `fallback` is true and there is a failure performing the clone,</span>
<span class="doccomment">/// then this function performs a standard [`std::fs::copy`]. Otherwise,</span>
<span class="doccomment">/// this function returns an error.</span>
<span class="attribute">#[<span class="ident">cfg</span>(<span class="ident">any</span>(<span class="ident">target_os</span> <span class="op">=</span> <span class="string">&quot;linux&quot;</span>, <span class="ident">target_os</span> <span class="op">=</span> <span class="string">&quot;android&quot;</span>))]</span>
<span class="kw">fn</span> <span class="ident">clone</span><span class="op">&lt;</span><span class="ident">P</span><span class="op">&gt;</span>(<span class="ident">source</span>: <span class="ident">P</span>, <span class="ident">dest</span>: <span class="ident">P</span>, <span class="ident">fallback</span>: <span class="ident">bool</span>) -&gt; <span class="ident">std::io::Result</span><span class="op">&lt;</span>()<span class="op">&gt;</span>
<span class="kw">where</span>
<span class="ident">P</span>: <span class="ident">AsRef</span><span class="op">&lt;</span><span class="ident">Path</span><span class="op">&gt;</span>,
{
<span class="kw">let</span> <span class="ident">src_file</span> <span class="op">=</span> <span class="ident">File::open</span>(<span class="kw-2">&amp;</span><span class="ident">source</span>)<span class="question-mark">?</span>;
<span class="kw">let</span> <span class="ident">dst_file</span> <span class="op">=</span> <span class="ident">File::create</span>(<span class="kw-2">&amp;</span><span class="ident">dest</span>)<span class="question-mark">?</span>;
<span class="kw">let</span> <span class="ident">src_fd</span> <span class="op">=</span> <span class="ident">src_file</span>.<span class="ident">as_raw_fd</span>();
<span class="kw">let</span> <span class="ident">dst_fd</span> <span class="op">=</span> <span class="ident">dst_file</span>.<span class="ident">as_raw_fd</span>();
<span class="kw">let</span> <span class="ident">result</span> <span class="op">=</span> <span class="kw">unsafe</span> { <span class="ident">libc::ioctl</span>(<span class="ident">dst_fd</span>, <span class="macro">FICLONE!</span>(), <span class="ident">src_fd</span>) };
<span class="kw">if</span> <span class="ident">result</span> <span class="op">!</span><span class="op">=</span> <span class="number">0</span> {
<span class="kw">if</span> <span class="ident">fallback</span> {
<span class="ident">std::fs::copy</span>(<span class="ident">source</span>, <span class="ident">dest</span>).<span class="ident">map</span>(<span class="op">|</span><span class="kw">_</span><span class="op">|</span> ())
} <span class="kw">else</span> {
<span class="prelude-val">Err</span>(<span class="ident">std::io::Error::last_os_error</span>())
}
} <span class="kw">else</span> {
<span class="prelude-val">Ok</span>(())
}
}
<span class="doccomment">/// Perform a sparse copy from one file to another.</span>
<span class="attribute">#[<span class="ident">cfg</span>(<span class="ident">any</span>(<span class="ident">target_os</span> <span class="op">=</span> <span class="string">&quot;linux&quot;</span>, <span class="ident">target_os</span> <span class="op">=</span> <span class="string">&quot;android&quot;</span>))]</span>
<span class="kw">fn</span> <span class="ident">sparse_copy</span><span class="op">&lt;</span><span class="ident">P</span><span class="op">&gt;</span>(<span class="ident">source</span>: <span class="ident">P</span>, <span class="ident">dest</span>: <span class="ident">P</span>) -&gt; <span class="ident">std::io::Result</span><span class="op">&lt;</span>()<span class="op">&gt;</span>
<span class="kw">where</span>
<span class="ident">P</span>: <span class="ident">AsRef</span><span class="op">&lt;</span><span class="ident">Path</span><span class="op">&gt;</span>,
{
<span class="kw">use</span> <span class="ident">std::os::unix::prelude::MetadataExt</span>;
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">src_file</span> <span class="op">=</span> <span class="ident">File::open</span>(<span class="ident">source</span>)<span class="question-mark">?</span>;
<span class="kw">let</span> <span class="ident">dst_file</span> <span class="op">=</span> <span class="ident">File::create</span>(<span class="ident">dest</span>)<span class="question-mark">?</span>;
<span class="kw">let</span> <span class="ident">dst_fd</span> <span class="op">=</span> <span class="ident">dst_file</span>.<span class="ident">as_raw_fd</span>();
<span class="kw">let</span> <span class="ident">size</span>: <span class="ident">usize</span> <span class="op">=</span> <span class="ident">src_file</span>.<span class="ident">metadata</span>()<span class="question-mark">?</span>.<span class="ident">size</span>().<span class="ident">try_into</span>().<span class="ident">unwrap</span>();
<span class="kw">if</span> <span class="kw">unsafe</span> { <span class="ident">libc::ftruncate</span>(<span class="ident">dst_fd</span>, <span class="ident">size</span>.<span class="ident">try_into</span>().<span class="ident">unwrap</span>()) } <span class="op">&lt;</span> <span class="number">0</span> {
<span class="kw">return</span> <span class="prelude-val">Err</span>(<span class="ident">std::io::Error::last_os_error</span>());
}
<span class="kw">let</span> <span class="ident">blksize</span> <span class="op">=</span> <span class="ident">dst_file</span>.<span class="ident">metadata</span>()<span class="question-mark">?</span>.<span class="ident">blksize</span>();
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">buf</span>: <span class="ident">Vec</span><span class="op">&lt;</span><span class="ident">u8</span><span class="op">&gt;</span> <span class="op">=</span> <span class="macro">vec!</span>[<span class="number">0</span>; <span class="ident">blksize</span>.<span class="ident">try_into</span>().<span class="ident">unwrap</span>()];
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">current_offset</span>: <span class="ident">usize</span> <span class="op">=</span> <span class="number">0</span>;
<span class="comment">// TODO Perhaps we can employ the &quot;fiemap ioctl&quot; API to get the</span>
<span class="comment">// file extent mappings:</span>
<span class="comment">// https://www.kernel.org/doc/html/latest/filesystems/fiemap.html</span>
<span class="kw">while</span> <span class="ident">current_offset</span> <span class="op">&lt;</span> <span class="ident">size</span> {
<span class="kw">let</span> <span class="ident">this_read</span> <span class="op">=</span> <span class="ident">src_file</span>.<span class="ident">read</span>(<span class="kw-2">&amp;mut</span> <span class="ident">buf</span>)<span class="question-mark">?</span>;
<span class="kw">if</span> <span class="ident">buf</span>.<span class="ident">iter</span>().<span class="ident">any</span>(<span class="op">|</span><span class="kw-2">&amp;</span><span class="ident">x</span><span class="op">|</span> <span class="ident">x</span> <span class="op">!</span><span class="op">=</span> <span class="number">0</span>) {
<span class="kw">unsafe</span> {
<span class="ident">libc::pwrite</span>(
<span class="ident">dst_fd</span>,
<span class="ident">buf</span>.<span class="ident">as_ptr</span>() <span class="kw">as</span> <span class="kw-2">*const</span> <span class="ident">libc::c_void</span>,
<span class="ident">this_read</span>,
<span class="ident">current_offset</span>.<span class="ident">try_into</span>().<span class="ident">unwrap</span>(),
)
};
}
<span class="ident">current_offset</span> <span class="op">+</span><span class="op">=</span> <span class="ident">this_read</span>;
}
<span class="prelude-val">Ok</span>(())
}
<span class="doccomment">/// Copies `source` to `dest` using copy-on-write if possible.</span>
<span class="attribute">#[<span class="ident">cfg</span>(<span class="ident">any</span>(<span class="ident">target_os</span> <span class="op">=</span> <span class="string">&quot;linux&quot;</span>, <span class="ident">target_os</span> <span class="op">=</span> <span class="string">&quot;android&quot;</span>))]</span>
<span class="kw">fn</span> <span class="ident">copy_on_write_linux</span>(
<span class="ident">source</span>: <span class="kw-2">&amp;</span><span class="ident">Path</span>,
<span class="ident">dest</span>: <span class="kw-2">&amp;</span><span class="ident">Path</span>,
<span class="ident">reflink_mode</span>: <span class="ident">ReflinkMode</span>,
<span class="ident">sparse_mode</span>: <span class="ident">SparseMode</span>,
<span class="ident">context</span>: <span class="kw-2">&amp;</span><span class="ident">str</span>,
) -&gt; <span class="ident">CopyResult</span><span class="op">&lt;</span>()<span class="op">&gt;</span> {
<span class="kw">let</span> <span class="ident">result</span> <span class="op">=</span> <span class="kw">match</span> (<span class="ident">reflink_mode</span>, <span class="ident">sparse_mode</span>) {
(<span class="ident">ReflinkMode::Never</span>, <span class="kw">_</span>) =&gt; <span class="ident">std::fs::copy</span>(<span class="ident">source</span>, <span class="ident">dest</span>).<span class="ident">map</span>(<span class="op">|</span><span class="kw">_</span><span class="op">|</span> ()),
(<span class="ident">ReflinkMode::Auto</span>, <span class="ident">SparseMode::Always</span>) =&gt; <span class="ident">sparse_copy</span>(<span class="ident">source</span>, <span class="ident">dest</span>),
(<span class="ident">ReflinkMode::Auto</span>, <span class="kw">_</span>) =&gt; <span class="ident">clone</span>(<span class="ident">source</span>, <span class="ident">dest</span>, <span class="bool-val">true</span>),
(<span class="ident">ReflinkMode::Always</span>, <span class="ident">SparseMode::Auto</span>) =&gt; <span class="ident">clone</span>(<span class="ident">source</span>, <span class="ident">dest</span>, <span class="bool-val">false</span>),
(<span class="ident">ReflinkMode::Always</span>, <span class="kw">_</span>) =&gt; {
<span class="kw">return</span> <span class="prelude-val">Err</span>(<span class="string">&quot;`--reflink=always` can be used only with --sparse=auto&quot;</span>.<span class="ident">into</span>())
}
};
<span class="ident">result</span>.<span class="ident">context</span>(<span class="ident">context</span>)<span class="question-mark">?</span>;
<span class="prelude-val">Ok</span>(())
}
<span class="doccomment">/// Copies `source` to `dest` using copy-on-write if possible.</span>
<span class="attribute">#[<span class="ident">cfg</span>(<span class="ident">target_os</span> <span class="op">=</span> <span class="string">&quot;macos&quot;</span>)]</span>
<span class="kw">fn</span> <span class="ident">copy_on_write_macos</span>(
<span class="ident">source</span>: <span class="kw-2">&amp;</span><span class="ident">Path</span>,
<span class="ident">dest</span>: <span class="kw-2">&amp;</span><span class="ident">Path</span>,
<span class="ident">reflink_mode</span>: <span class="ident">ReflinkMode</span>,
<span class="ident">sparse_mode</span>: <span class="ident">SparseMode</span>,
<span class="ident">context</span>: <span class="kw-2">&amp;</span><span class="ident">str</span>,
) -&gt; <span class="ident">CopyResult</span><span class="op">&lt;</span>()<span class="op">&gt;</span> {
<span class="kw">if</span> <span class="ident">sparse_mode</span> <span class="op">!</span><span class="op">=</span> <span class="ident">SparseMode::Auto</span> {
<span class="kw">return</span> <span class="prelude-val">Err</span>(<span class="string">&quot;--sparse is only supported on linux&quot;</span>.<span class="ident">to_string</span>().<span class="ident">into</span>());
}
<span class="comment">// Extract paths in a form suitable to be passed to a syscall.</span>
<span class="comment">// The unwrap() is safe because they come from the command-line and so contain non nul</span>
<span class="comment">// character.</span>
<span class="kw">let</span> <span class="ident">src</span> <span class="op">=</span> <span class="ident">CString::new</span>(<span class="ident">source</span>.<span class="ident">as_os_str</span>().<span class="ident">as_bytes</span>()).<span class="ident">unwrap</span>();
<span class="kw">let</span> <span class="ident">dst</span> <span class="op">=</span> <span class="ident">CString::new</span>(<span class="ident">dest</span>.<span class="ident">as_os_str</span>().<span class="ident">as_bytes</span>()).<span class="ident">unwrap</span>();
<span class="comment">// clonefile(2) was introduced in macOS 10.12 so we cannot statically link against it</span>
<span class="comment">// for backward compatibility.</span>
<span class="kw">let</span> <span class="ident">clonefile</span> <span class="op">=</span> <span class="ident">CString::new</span>(<span class="string">&quot;clonefile&quot;</span>).<span class="ident">unwrap</span>();
<span class="kw">let</span> <span class="ident">raw_pfn</span> <span class="op">=</span> <span class="kw">unsafe</span> { <span class="ident">libc::dlsym</span>(<span class="ident">libc::RTLD_NEXT</span>, <span class="ident">clonefile</span>.<span class="ident">as_ptr</span>()) };
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">error</span> <span class="op">=</span> <span class="number">0</span>;
<span class="kw">if</span> <span class="op">!</span><span class="ident">raw_pfn</span>.<span class="ident">is_null</span>() {
<span class="comment">// Call clonefile(2).</span>
<span class="comment">// Safety: Casting a C function pointer to a rust function value is one of the few</span>
<span class="comment">// blessed uses of `transmute()`.</span>
<span class="kw">unsafe</span> {
<span class="kw">let</span> <span class="ident">pfn</span>: <span class="kw">extern</span> <span class="string">&quot;C&quot;</span> <span class="kw">fn</span>(
<span class="ident">src</span>: <span class="kw-2">*const</span> <span class="ident">libc::c_char</span>,
<span class="ident">dst</span>: <span class="kw-2">*const</span> <span class="ident">libc::c_char</span>,
<span class="ident">flags</span>: <span class="ident">u32</span>,
) -&gt; <span class="ident">libc::c_int</span> <span class="op">=</span> <span class="ident">std::mem::transmute</span>(<span class="ident">raw_pfn</span>);
<span class="ident">error</span> <span class="op">=</span> <span class="ident">pfn</span>(<span class="ident">src</span>.<span class="ident">as_ptr</span>(), <span class="ident">dst</span>.<span class="ident">as_ptr</span>(), <span class="number">0</span>);
<span class="kw">if</span> <span class="ident">std::io::Error::last_os_error</span>().<span class="ident">kind</span>() <span class="op">==</span> <span class="ident">std::io::ErrorKind::AlreadyExists</span> {
<span class="comment">// clonefile(2) fails if the destination exists. Remove it and try again. Do not</span>
<span class="comment">// bother to check if removal worked because we&#39;re going to try to clone again.</span>
<span class="kw">let</span> <span class="kw">_</span> <span class="op">=</span> <span class="ident">fs::remove_file</span>(<span class="ident">dest</span>);
<span class="ident">error</span> <span class="op">=</span> <span class="ident">pfn</span>(<span class="ident">src</span>.<span class="ident">as_ptr</span>(), <span class="ident">dst</span>.<span class="ident">as_ptr</span>(), <span class="number">0</span>);
}
}
}
<span class="kw">if</span> <span class="ident">raw_pfn</span>.<span class="ident">is_null</span>() <span class="op">|</span><span class="op">|</span> <span class="ident">error</span> <span class="op">!</span><span class="op">=</span> <span class="number">0</span> {
<span class="comment">// clonefile(2) is either not supported or it errored out (possibly because the FS does not</span>
<span class="comment">// support COW).</span>
<span class="kw">match</span> <span class="ident">reflink_mode</span> {
<span class="ident">ReflinkMode::Always</span> =&gt; {
<span class="kw">return</span> <span class="prelude-val">Err</span>(
<span class="macro">format!</span>(<span class="string">&quot;failed to clone {:?} from {:?}: {}&quot;</span>, <span class="ident">source</span>, <span class="ident">dest</span>, <span class="ident">error</span>).<span class="ident">into</span>(),
)
}
<span class="ident">ReflinkMode::Auto</span> =&gt; <span class="ident">fs::copy</span>(<span class="ident">source</span>, <span class="ident">dest</span>).<span class="ident">context</span>(<span class="ident">context</span>)<span class="question-mark">?</span>,
<span class="ident">ReflinkMode::Never</span> =&gt; <span class="ident">fs::copy</span>(<span class="ident">source</span>, <span class="ident">dest</span>).<span class="ident">context</span>(<span class="ident">context</span>)<span class="question-mark">?</span>,
};
}
<span class="prelude-val">Ok</span>(())
}
<span class="doccomment">/// Generate an error message if `target` is not the correct `target_type`</span>
<span class="kw">pub</span> <span class="kw">fn</span> <span class="ident">verify_target_type</span>(<span class="ident">target</span>: <span class="kw-2">&amp;</span><span class="ident">Path</span>, <span class="ident">target_type</span>: <span class="kw-2">&amp;</span><span class="ident">TargetType</span>) -&gt; <span class="ident">CopyResult</span><span class="op">&lt;</span>()<span class="op">&gt;</span> {
<span class="kw">match</span> (<span class="ident">target_type</span>, <span class="ident">target</span>.<span class="ident">is_dir</span>()) {
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
+103 -13
View File
@@ -209,6 +209,51 @@
<span id="209">209</span>
<span id="210">210</span>
<span id="211">211</span>
<span id="212">212</span>
<span id="213">213</span>
<span id="214">214</span>
<span id="215">215</span>
<span id="216">216</span>
<span id="217">217</span>
<span id="218">218</span>
<span id="219">219</span>
<span id="220">220</span>
<span id="221">221</span>
<span id="222">222</span>
<span id="223">223</span>
<span id="224">224</span>
<span id="225">225</span>
<span id="226">226</span>
<span id="227">227</span>
<span id="228">228</span>
<span id="229">229</span>
<span id="230">230</span>
<span id="231">231</span>
<span id="232">232</span>
<span id="233">233</span>
<span id="234">234</span>
<span id="235">235</span>
<span id="236">236</span>
<span id="237">237</span>
<span id="238">238</span>
<span id="239">239</span>
<span id="240">240</span>
<span id="241">241</span>
<span id="242">242</span>
<span id="243">243</span>
<span id="244">244</span>
<span id="245">245</span>
<span id="246">246</span>
<span id="247">247</span>
<span id="248">248</span>
<span id="249">249</span>
<span id="250">250</span>
<span id="251">251</span>
<span id="252">252</span>
<span id="253">253</span>
<span id="254">254</span>
<span id="255">255</span>
<span id="256">256</span>
</pre><pre class="rust"><code><span class="comment">// * This file is part of the uutils coreutils package.</span>
<span class="comment">// *</span>
<span class="comment">// * For the full copyright and license information, please view the LICENSE</span>
@@ -239,6 +284,7 @@
<span class="kw">use</span> <span class="ident"><span class="kw">crate</span>::number::DynamicWidthNumber</span>;
<span class="kw">use</span> <span class="ident"><span class="kw">crate</span>::number::FixedWidthNumber</span>;
<span class="kw">use</span> <span class="ident"><span class="kw">crate</span>::number::Number</span>;
<span class="kw">use</span> <span class="ident">uucore::error</span>::{<span class="ident">UResult</span>, <span class="ident">USimpleError</span>};
<span class="doccomment">/// The format to use for suffixes in the filename for each output chunk.</span>
<span class="attribute">#[<span class="ident">derive</span>(<span class="ident">Clone</span>, <span class="ident">Copy</span>)]</span>
@@ -330,19 +376,28 @@
<span class="ident">additional_suffix</span>: <span class="kw-2">&amp;</span><span class="lifetime">&#39;a</span> <span class="ident">str</span>,
<span class="ident">suffix_length</span>: <span class="ident">usize</span>,
<span class="ident">suffix_type</span>: <span class="ident">SuffixType</span>,
) -&gt; <span class="ident">FilenameIterator</span><span class="op">&lt;</span><span class="lifetime">&#39;a</span><span class="op">&gt;</span> {
<span class="ident">suffix_start</span>: <span class="ident">usize</span>,
) -&gt; <span class="ident">UResult</span><span class="op">&lt;</span><span class="ident">FilenameIterator</span><span class="op">&lt;</span><span class="lifetime">&#39;a</span><span class="op">&gt;</span><span class="op">&gt;</span> {
<span class="kw">let</span> <span class="ident">radix</span> <span class="op">=</span> <span class="ident">suffix_type</span>.<span class="ident">radix</span>();
<span class="kw">let</span> <span class="ident">number</span> <span class="op">=</span> <span class="kw">if</span> <span class="ident">suffix_length</span> <span class="op">==</span> <span class="number">0</span> {
<span class="ident">Number::DynamicWidth</span>(<span class="ident">DynamicWidthNumber::new</span>(<span class="ident">radix</span>))
<span class="ident">Number::DynamicWidth</span>(<span class="ident">DynamicWidthNumber::new</span>(<span class="ident">radix</span>, <span class="ident">suffix_start</span>))
} <span class="kw">else</span> {
<span class="ident">Number::FixedWidth</span>(<span class="ident">FixedWidthNumber::new</span>(<span class="ident">radix</span>, <span class="ident">suffix_length</span>))
<span class="ident">Number::FixedWidth</span>(
<span class="ident">FixedWidthNumber::new</span>(<span class="ident">radix</span>, <span class="ident">suffix_length</span>, <span class="ident">suffix_start</span>).<span class="ident">map_err</span>(<span class="op">|</span><span class="kw">_</span><span class="op">|</span> {
<span class="ident">USimpleError::new</span>(
<span class="number">1</span>,
<span class="string">&quot;numerical suffix start value is too large for the suffix length&quot;</span>,
)
})<span class="question-mark">?</span>,
)
};
<span class="ident">FilenameIterator</span> {
<span class="prelude-val">Ok</span>(<span class="ident">FilenameIterator</span> {
<span class="ident">prefix</span>,
<span class="ident">additional_suffix</span>,
<span class="ident">number</span>,
<span class="ident">first_iteration</span>: <span class="bool-val">true</span>,
}
})
}
}
@@ -372,36 +427,36 @@
<span class="attribute">#[<span class="ident">test</span>]</span>
<span class="kw">fn</span> <span class="ident">test_filename_iterator_alphabetic_fixed_width</span>() {
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">it</span> <span class="op">=</span> <span class="ident">FilenameIterator::new</span>(<span class="string">&quot;chunk_&quot;</span>, <span class="string">&quot;.txt&quot;</span>, <span class="number">2</span>, <span class="ident">SuffixType::Alphabetic</span>);
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">it</span> <span class="op">=</span> <span class="ident">FilenameIterator::new</span>(<span class="string">&quot;chunk_&quot;</span>, <span class="string">&quot;.txt&quot;</span>, <span class="number">2</span>, <span class="ident">SuffixType::Alphabetic</span>, <span class="number">0</span>).<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_aa.txt&quot;</span>);
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_ab.txt&quot;</span>);
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_ac.txt&quot;</span>);
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">it</span> <span class="op">=</span> <span class="ident">FilenameIterator::new</span>(<span class="string">&quot;chunk_&quot;</span>, <span class="string">&quot;.txt&quot;</span>, <span class="number">2</span>, <span class="ident">SuffixType::Alphabetic</span>);
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">it</span> <span class="op">=</span> <span class="ident">FilenameIterator::new</span>(<span class="string">&quot;chunk_&quot;</span>, <span class="string">&quot;.txt&quot;</span>, <span class="number">2</span>, <span class="ident">SuffixType::Alphabetic</span>, <span class="number">0</span>).<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">nth</span>(<span class="number">26</span> <span class="op">*</span> <span class="number">26</span> <span class="op">-</span> <span class="number">1</span>).<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_zz.txt&quot;</span>);
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>(), <span class="prelude-val">None</span>);
}
<span class="attribute">#[<span class="ident">test</span>]</span>
<span class="kw">fn</span> <span class="ident">test_filename_iterator_numeric_fixed_width</span>() {
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">it</span> <span class="op">=</span> <span class="ident">FilenameIterator::new</span>(<span class="string">&quot;chunk_&quot;</span>, <span class="string">&quot;.txt&quot;</span>, <span class="number">2</span>, <span class="ident">SuffixType::Decimal</span>);
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">it</span> <span class="op">=</span> <span class="ident">FilenameIterator::new</span>(<span class="string">&quot;chunk_&quot;</span>, <span class="string">&quot;.txt&quot;</span>, <span class="number">2</span>, <span class="ident">SuffixType::Decimal</span>, <span class="number">0</span>).<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_00.txt&quot;</span>);
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_01.txt&quot;</span>);
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_02.txt&quot;</span>);
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">it</span> <span class="op">=</span> <span class="ident">FilenameIterator::new</span>(<span class="string">&quot;chunk_&quot;</span>, <span class="string">&quot;.txt&quot;</span>, <span class="number">2</span>, <span class="ident">SuffixType::Decimal</span>);
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">it</span> <span class="op">=</span> <span class="ident">FilenameIterator::new</span>(<span class="string">&quot;chunk_&quot;</span>, <span class="string">&quot;.txt&quot;</span>, <span class="number">2</span>, <span class="ident">SuffixType::Decimal</span>, <span class="number">0</span>).<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">nth</span>(<span class="number">10</span> <span class="op">*</span> <span class="number">10</span> <span class="op">-</span> <span class="number">1</span>).<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_99.txt&quot;</span>);
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>(), <span class="prelude-val">None</span>);
}
<span class="attribute">#[<span class="ident">test</span>]</span>
<span class="kw">fn</span> <span class="ident">test_filename_iterator_alphabetic_dynamic_width</span>() {
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">it</span> <span class="op">=</span> <span class="ident">FilenameIterator::new</span>(<span class="string">&quot;chunk_&quot;</span>, <span class="string">&quot;.txt&quot;</span>, <span class="number">0</span>, <span class="ident">SuffixType::Alphabetic</span>);
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">it</span> <span class="op">=</span> <span class="ident">FilenameIterator::new</span>(<span class="string">&quot;chunk_&quot;</span>, <span class="string">&quot;.txt&quot;</span>, <span class="number">0</span>, <span class="ident">SuffixType::Alphabetic</span>, <span class="number">0</span>).<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_aa.txt&quot;</span>);
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_ab.txt&quot;</span>);
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_ac.txt&quot;</span>);
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">it</span> <span class="op">=</span> <span class="ident">FilenameIterator::new</span>(<span class="string">&quot;chunk_&quot;</span>, <span class="string">&quot;.txt&quot;</span>, <span class="number">0</span>, <span class="ident">SuffixType::Alphabetic</span>);
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">it</span> <span class="op">=</span> <span class="ident">FilenameIterator::new</span>(<span class="string">&quot;chunk_&quot;</span>, <span class="string">&quot;.txt&quot;</span>, <span class="number">0</span>, <span class="ident">SuffixType::Alphabetic</span>, <span class="number">0</span>).<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">nth</span>(<span class="number">26</span> <span class="op">*</span> <span class="number">25</span> <span class="op">-</span> <span class="number">1</span>).<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_yz.txt&quot;</span>);
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_zaaa.txt&quot;</span>);
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_zaab.txt&quot;</span>);
@@ -409,16 +464,51 @@
<span class="attribute">#[<span class="ident">test</span>]</span>
<span class="kw">fn</span> <span class="ident">test_filename_iterator_numeric_dynamic_width</span>() {
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">it</span> <span class="op">=</span> <span class="ident">FilenameIterator::new</span>(<span class="string">&quot;chunk_&quot;</span>, <span class="string">&quot;.txt&quot;</span>, <span class="number">0</span>, <span class="ident">SuffixType::Decimal</span>);
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">it</span> <span class="op">=</span> <span class="ident">FilenameIterator::new</span>(<span class="string">&quot;chunk_&quot;</span>, <span class="string">&quot;.txt&quot;</span>, <span class="number">0</span>, <span class="ident">SuffixType::Decimal</span>, <span class="number">0</span>).<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_00.txt&quot;</span>);
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_01.txt&quot;</span>);
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_02.txt&quot;</span>);
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">it</span> <span class="op">=</span> <span class="ident">FilenameIterator::new</span>(<span class="string">&quot;chunk_&quot;</span>, <span class="string">&quot;.txt&quot;</span>, <span class="number">0</span>, <span class="ident">SuffixType::Decimal</span>);
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">it</span> <span class="op">=</span> <span class="ident">FilenameIterator::new</span>(<span class="string">&quot;chunk_&quot;</span>, <span class="string">&quot;.txt&quot;</span>, <span class="number">0</span>, <span class="ident">SuffixType::Decimal</span>, <span class="number">0</span>).<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">nth</span>(<span class="number">10</span> <span class="op">*</span> <span class="number">9</span> <span class="op">-</span> <span class="number">1</span>).<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_89.txt&quot;</span>);
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_9000.txt&quot;</span>);
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_9001.txt&quot;</span>);
}
<span class="attribute">#[<span class="ident">test</span>]</span>
<span class="kw">fn</span> <span class="ident">test_filename_iterator_numeric_suffix_decimal</span>() {
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">it</span> <span class="op">=</span> <span class="ident">FilenameIterator::new</span>(<span class="string">&quot;chunk_&quot;</span>, <span class="string">&quot;.txt&quot;</span>, <span class="number">0</span>, <span class="ident">SuffixType::Decimal</span>, <span class="number">5</span>).<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_05.txt&quot;</span>);
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_06.txt&quot;</span>);
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_07.txt&quot;</span>);
}
<span class="attribute">#[<span class="ident">test</span>]</span>
<span class="kw">fn</span> <span class="ident">test_filename_iterator_numeric_suffix_hex</span>() {
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">it</span> <span class="op">=</span>
<span class="ident">FilenameIterator::new</span>(<span class="string">&quot;chunk_&quot;</span>, <span class="string">&quot;.txt&quot;</span>, <span class="number">0</span>, <span class="ident">SuffixType::Hexadecimal</span>, <span class="number">9</span>).<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_09.txt&quot;</span>);
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_0a.txt&quot;</span>);
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_0b.txt&quot;</span>);
}
<span class="attribute">#[<span class="ident">test</span>]</span>
<span class="kw">fn</span> <span class="ident">test_filename_iterator_numeric_suffix_err</span>() {
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">it</span> <span class="op">=</span> <span class="ident">FilenameIterator::new</span>(<span class="string">&quot;chunk_&quot;</span>, <span class="string">&quot;.txt&quot;</span>, <span class="number">3</span>, <span class="ident">SuffixType::Decimal</span>, <span class="number">999</span>).<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_999.txt&quot;</span>);
<span class="macro">assert!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">is_none</span>());
<span class="kw">let</span> <span class="ident">it</span> <span class="op">=</span> <span class="ident">FilenameIterator::new</span>(<span class="string">&quot;chunk_&quot;</span>, <span class="string">&quot;.txt&quot;</span>, <span class="number">3</span>, <span class="ident">SuffixType::Decimal</span>, <span class="number">1000</span>);
<span class="macro">assert!</span>(<span class="ident">it</span>.<span class="ident">is_err</span>());
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">it</span> <span class="op">=</span>
<span class="ident">FilenameIterator::new</span>(<span class="string">&quot;chunk_&quot;</span>, <span class="string">&quot;.txt&quot;</span>, <span class="number">3</span>, <span class="ident">SuffixType::Hexadecimal</span>, <span class="number">0xfff</span>).<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">unwrap</span>(), <span class="string">&quot;chunk_fff.txt&quot;</span>);
<span class="macro">assert!</span>(<span class="ident">it</span>.<span class="ident">next</span>().<span class="ident">is_none</span>());
<span class="kw">let</span> <span class="ident">it</span> <span class="op">=</span> <span class="ident">FilenameIterator::new</span>(<span class="string">&quot;chunk_&quot;</span>, <span class="string">&quot;.txt&quot;</span>, <span class="number">3</span>, <span class="ident">SuffixType::Hexadecimal</span>, <span class="number">0x1000</span>);
<span class="macro">assert!</span>(<span class="ident">it</span>.<span class="ident">is_err</span>());
}
}
</code></pre></div>
</section></div></main><div id="rustdoc-vars" data-root-path="../../" data-current-crate="uu_split" data-themes="ayu,dark,light" data-resource-suffix="" data-rustdoc-version="1.64.0 (a55dd71d5 2022-09-19)" ></div></body></html>
+132 -140
View File
@@ -580,10 +580,6 @@
<span id="580">580</span>
<span id="581">581</span>
<span id="582">582</span>
<span id="583">583</span>
<span id="584">584</span>
<span id="585">585</span>
<span id="586">586</span>
</pre><pre class="rust"><code><span class="comment">// * This file is part of the uutils coreutils package.</span>
<span class="comment">// *</span>
<span class="comment">// * For the full copyright and license information, please view the LICENSE</span>
@@ -686,10 +682,10 @@
<span class="doccomment">/// differently and we only intend to use these numbers for display</span>
<span class="doccomment">/// purposes and not for mathematical purposes.</span>
<span class="attribute">#[<span class="ident">allow</span>(<span class="ident">dead_code</span>)]</span>
<span class="kw">fn</span> <span class="ident">digits</span>(<span class="kw-2">&amp;</span><span class="self">self</span>) -&gt; <span class="kw-2">&amp;</span><span class="ident">Vec</span><span class="op">&lt;</span><span class="ident">u8</span><span class="op">&gt;</span> {
<span class="kw">fn</span> <span class="ident">digits</span>(<span class="kw-2">&amp;</span><span class="self">self</span>) -&gt; <span class="ident">Vec</span><span class="op">&lt;</span><span class="ident">u8</span><span class="op">&gt;</span> {
<span class="kw">match</span> <span class="self">self</span> {
<span class="ident"><span class="self">Self</span>::FixedWidth</span>(<span class="ident">number</span>) =&gt; <span class="kw-2">&amp;</span><span class="ident">number</span>.<span class="ident">digits</span>,
<span class="ident"><span class="self">Self</span>::DynamicWidth</span>(<span class="ident">number</span>) =&gt; <span class="kw-2">&amp;</span><span class="ident">number</span>.<span class="ident">digits</span>,
<span class="ident"><span class="self">Self</span>::FixedWidth</span>(<span class="ident">number</span>) =&gt; <span class="ident">number</span>.<span class="ident">digits</span>.<span class="ident">clone</span>(),
<span class="ident"><span class="self">Self</span>::DynamicWidth</span>(<span class="ident">number</span>) =&gt; <span class="ident">number</span>.<span class="ident">digits</span>(),
}
}
@@ -761,7 +757,7 @@
<span class="doccomment">///</span>
<span class="doccomment">/// # Displaying</span>
<span class="doccomment">///</span>
<span class="doccomment">/// This number is only displayable if `radix` is 10, 26, or 26. If</span>
<span class="doccomment">/// This number is only displayable if `radix` is 10, 16, or 26. If</span>
<span class="doccomment">/// `radix` is 10 or 16, then the digits are concatenated and</span>
<span class="doccomment">/// displayed as a fixed-width decimal or hexadecimal number,</span>
<span class="doccomment">/// respectively. If `radix` is 26, then each digit is translated to</span>
@@ -775,10 +771,21 @@
<span class="kw">impl</span> <span class="ident">FixedWidthNumber</span> {
<span class="doccomment">/// Instantiate a number of the given radix and width.</span>
<span class="kw">pub</span> <span class="kw">fn</span> <span class="ident">new</span>(<span class="ident">radix</span>: <span class="ident">u8</span>, <span class="ident">width</span>: <span class="ident">usize</span>) -&gt; <span class="self">Self</span> {
<span class="self">Self</span> {
<span class="ident">radix</span>,
<span class="ident">digits</span>: <span class="macro">vec!</span>[<span class="number">0</span>; <span class="ident">width</span>],
<span class="kw">pub</span> <span class="kw">fn</span> <span class="ident">new</span>(<span class="ident">radix</span>: <span class="ident">u8</span>, <span class="ident">width</span>: <span class="ident">usize</span>, <span class="kw-2">mut</span> <span class="ident">suffix_start</span>: <span class="ident">usize</span>) -&gt; <span class="prelude-ty">Result</span><span class="op">&lt;</span><span class="self">Self</span>, <span class="ident">Overflow</span><span class="op">&gt;</span> {
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">digits</span> <span class="op">=</span> <span class="macro">vec!</span>[<span class="number">0_u8</span>; <span class="ident">width</span>];
<span class="kw">for</span> <span class="ident">i</span> <span class="kw">in</span> (<span class="number">0</span>..<span class="ident">digits</span>.<span class="ident">len</span>()).<span class="ident">rev</span>() {
<span class="kw">let</span> <span class="ident">remainder</span> <span class="op">=</span> (<span class="ident">suffix_start</span> <span class="op">%</span> (<span class="ident">radix</span> <span class="kw">as</span> <span class="ident">usize</span>)) <span class="kw">as</span> <span class="ident">u8</span>;
<span class="ident">suffix_start</span> <span class="op">/</span><span class="op">=</span> <span class="ident">radix</span> <span class="kw">as</span> <span class="ident">usize</span>;
<span class="ident">digits</span>[<span class="ident">i</span>] <span class="op">=</span> <span class="ident">remainder</span>;
<span class="kw">if</span> <span class="ident">suffix_start</span> <span class="op">==</span> <span class="number">0</span> {
<span class="kw">break</span>;
}
}
<span class="kw">if</span> <span class="ident">suffix_start</span> <span class="op">!</span><span class="op">=</span> <span class="number">0</span> {
<span class="prelude-val">Err</span>(<span class="ident">Overflow</span>)
} <span class="kw">else</span> {
<span class="prelude-val">Ok</span>(<span class="self">Self</span> { <span class="ident">radix</span>, <span class="ident">digits</span> })
}
}
@@ -815,25 +822,12 @@
<span class="kw">impl</span> <span class="ident">Display</span> <span class="kw">for</span> <span class="ident">FixedWidthNumber</span> {
<span class="kw">fn</span> <span class="ident">fmt</span>(<span class="kw-2">&amp;</span><span class="self">self</span>, <span class="ident">f</span>: <span class="kw-2">&amp;mut</span> <span class="ident">Formatter</span>) -&gt; <span class="ident">fmt::Result</span> {
<span class="kw">match</span> <span class="self">self</span>.<span class="ident">radix</span> {
<span class="number">10</span> =&gt; {
<span class="kw">let</span> <span class="ident">digits</span>: <span class="ident">String</span> <span class="op">=</span> <span class="self">self</span>.<span class="ident">digits</span>.<span class="ident">iter</span>().<span class="ident">map</span>(<span class="op">|</span><span class="ident">d</span><span class="op">|</span> (<span class="string">b&#39;0&#39;</span> <span class="op">+</span> <span class="ident">d</span>) <span class="kw">as</span> <span class="ident">char</span>).<span class="ident">collect</span>();
<span class="macro">write!</span>(<span class="ident">f</span>, <span class="string">&quot;{}&quot;</span>, <span class="ident">digits</span>)
}
<span class="number">16</span> =&gt; {
<span class="kw">let</span> <span class="ident">digits</span>: <span class="ident">String</span> <span class="op">=</span> <span class="self">self</span>
.<span class="ident">digits</span>
.<span class="ident">iter</span>()
.<span class="ident">map</span>(<span class="op">|</span><span class="ident">d</span><span class="op">|</span> (<span class="kw">if</span> <span class="kw-2">*</span><span class="ident">d</span> <span class="op">&lt;</span> <span class="number">10</span> { <span class="string">b&#39;0&#39;</span> <span class="op">+</span> <span class="ident">d</span> } <span class="kw">else</span> { <span class="string">b&#39;a&#39;</span> <span class="op">+</span> (<span class="ident">d</span> <span class="op">-</span> <span class="number">10</span>) }) <span class="kw">as</span> <span class="ident">char</span>)
.<span class="ident">collect</span>();
<span class="macro">write!</span>(<span class="ident">f</span>, <span class="string">&quot;{}&quot;</span>, <span class="ident">digits</span>)
}
<span class="number">26</span> =&gt; {
<span class="kw">let</span> <span class="ident">digits</span>: <span class="ident">String</span> <span class="op">=</span> <span class="self">self</span>.<span class="ident">digits</span>.<span class="ident">iter</span>().<span class="ident">map</span>(<span class="op">|</span><span class="ident">d</span><span class="op">|</span> (<span class="string">b&#39;a&#39;</span> <span class="op">+</span> <span class="ident">d</span>) <span class="kw">as</span> <span class="ident">char</span>).<span class="ident">collect</span>();
<span class="macro">write!</span>(<span class="ident">f</span>, <span class="string">&quot;{}&quot;</span>, <span class="ident">digits</span>)
}
<span class="kw">_</span> =&gt; <span class="prelude-val">Err</span>(<span class="ident">fmt::Error</span>),
}
<span class="kw">let</span> <span class="ident">digits</span>: <span class="ident">String</span> <span class="op">=</span> <span class="self">self</span>
.<span class="ident">digits</span>
.<span class="ident">iter</span>()
.<span class="ident">map</span>(<span class="op">|</span><span class="ident">d</span><span class="op">|</span> <span class="ident">map_digit</span>(<span class="self">self</span>.<span class="ident">radix</span>, <span class="kw-2">*</span><span class="ident">d</span>))
.<span class="ident">collect</span>();
<span class="macro">write!</span>(<span class="ident">f</span>, <span class="string">&quot;{}&quot;</span>, <span class="ident">digits</span>)
}
}
@@ -879,105 +873,74 @@
<span class="attribute">#[<span class="ident">derive</span>(<span class="ident">Clone</span>)]</span>
<span class="kw">pub</span> <span class="kw">struct</span> <span class="ident">DynamicWidthNumber</span> {
<span class="ident">radix</span>: <span class="ident">u8</span>,
<span class="ident">digits</span>: <span class="ident">Vec</span><span class="op">&lt;</span><span class="ident">u8</span><span class="op">&gt;</span>,
<span class="ident">current</span>: <span class="ident">usize</span>,
}
<span class="kw">impl</span> <span class="ident">DynamicWidthNumber</span> {
<span class="doccomment">/// Instantiate a number of the given radix, starting with width 2.</span>
<span class="doccomment">///</span>
<span class="doccomment">/// This associated function returns a new instance of the struct</span>
<span class="doccomment">/// with the given radix and a width of two digits, both 0.</span>
<span class="kw">pub</span> <span class="kw">fn</span> <span class="ident">new</span>(<span class="ident">radix</span>: <span class="ident">u8</span>) -&gt; <span class="self">Self</span> {
<span class="kw">pub</span> <span class="kw">fn</span> <span class="ident">new</span>(<span class="ident">radix</span>: <span class="ident">u8</span>, <span class="ident">suffix_start</span>: <span class="ident">usize</span>) -&gt; <span class="self">Self</span> {
<span class="self">Self</span> {
<span class="ident">radix</span>,
<span class="ident">digits</span>: <span class="macro">vec!</span>[<span class="number">0</span>, <span class="number">0</span>],
<span class="ident">current</span>: <span class="ident">suffix_start</span>,
}
}
<span class="doccomment">/// Set all digits to zero.</span>
<span class="kw">fn</span> <span class="ident">reset</span>(<span class="kw-2">&amp;mut</span> <span class="self">self</span>) {
<span class="kw">for</span> <span class="ident">i</span> <span class="kw">in</span> <span class="number">0</span>..<span class="self">self</span>.<span class="ident">digits</span>.<span class="ident">len</span>() {
<span class="self">self</span>.<span class="ident">digits</span>[<span class="ident">i</span>] <span class="op">=</span> <span class="number">0</span>;
}
}
<span class="doccomment">/// Increment this number.</span>
<span class="doccomment">///</span>
<span class="doccomment">/// This method adds one to this number. The first time that the</span>
<span class="doccomment">/// most significant digit would achieve its highest possible</span>
<span class="doccomment">/// value (that is, `radix - 1`), then all the digits get reset to</span>
<span class="doccomment">/// 0 and the number of digits increases by one.</span>
<span class="doccomment">///</span>
<span class="doccomment">/// This method never returns an error.</span>
<span class="kw">fn</span> <span class="ident">increment</span>(<span class="kw-2">&amp;mut</span> <span class="self">self</span>) -&gt; <span class="prelude-ty">Result</span><span class="op">&lt;</span>(), <span class="ident">Overflow</span><span class="op">&gt;</span> {
<span class="kw">for</span> <span class="ident">i</span> <span class="kw">in</span> (<span class="number">0</span>..<span class="self">self</span>.<span class="ident">digits</span>.<span class="ident">len</span>()).<span class="ident">rev</span>() {
<span class="comment">// Increment the current digit.</span>
<span class="self">self</span>.<span class="ident">digits</span>[<span class="ident">i</span>] <span class="op">+</span><span class="op">=</span> <span class="number">1</span>;
<span class="comment">// If the digit overflows, then set it to 0 and continue</span>
<span class="comment">// to the next iteration to increment the next most</span>
<span class="comment">// significant digit. Otherwise, terminate the loop, since</span>
<span class="comment">// there will be no further changes to any higher order</span>
<span class="comment">// digits.</span>
<span class="kw">if</span> <span class="self">self</span>.<span class="ident">digits</span>[<span class="ident">i</span>] <span class="op">==</span> <span class="self">self</span>.<span class="ident">radix</span> {
<span class="self">self</span>.<span class="ident">digits</span>[<span class="ident">i</span>] <span class="op">=</span> <span class="number">0</span>;
} <span class="kw">else</span> {
<span class="kw">break</span>;
}
}
<span class="comment">// If the most significant digit is at its maximum value, then</span>
<span class="comment">// add another digit and reset all digits zero.</span>
<span class="kw">if</span> <span class="self">self</span>.<span class="ident">digits</span>[<span class="number">0</span>] <span class="op">==</span> <span class="self">self</span>.<span class="ident">radix</span> <span class="op">-</span> <span class="number">1</span> {
<span class="self">self</span>.<span class="ident">digits</span>.<span class="ident">push</span>(<span class="number">0</span>);
<span class="self">self</span>.<span class="ident">reset</span>();
}
<span class="self">self</span>.<span class="ident">current</span> <span class="op">+</span><span class="op">=</span> <span class="number">1</span>;
<span class="prelude-val">Ok</span>(())
}
<span class="kw">fn</span> <span class="ident">digits</span>(<span class="kw-2">&amp;</span><span class="self">self</span>) -&gt; <span class="ident">Vec</span><span class="op">&lt;</span><span class="ident">u8</span><span class="op">&gt;</span> {
<span class="kw">let</span> <span class="ident">radix</span> <span class="op">=</span> <span class="self">self</span>.<span class="ident">radix</span> <span class="kw">as</span> <span class="ident">usize</span>;
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">remaining</span> <span class="op">=</span> <span class="self">self</span>.<span class="ident">current</span>;
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">sub_value</span> <span class="op">=</span> (<span class="ident">radix</span> <span class="op">-</span> <span class="number">1</span>) <span class="op">*</span> <span class="ident">radix</span>;
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">num_fill_chars</span> <span class="op">=</span> <span class="number">2</span>;
<span class="comment">// Convert the number into &quot;num_fill_chars&quot; and &quot;remaining&quot;</span>
<span class="kw">while</span> <span class="ident">remaining</span> <span class="op">&gt;</span><span class="op">=</span> <span class="ident">sub_value</span> {
<span class="ident">remaining</span> <span class="op">-</span><span class="op">=</span> <span class="ident">sub_value</span>;
<span class="ident">sub_value</span> <span class="kw-2">*</span><span class="op">=</span> <span class="ident">radix</span>;
<span class="ident">num_fill_chars</span> <span class="op">+</span><span class="op">=</span> <span class="number">1</span>;
}
<span class="comment">// Convert the &quot;remainder&quot; to digits</span>
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">digits</span> <span class="op">=</span> <span class="ident">Vec::new</span>();
<span class="kw">while</span> <span class="ident">remaining</span> <span class="op">&gt;</span> <span class="number">0</span> {
<span class="ident">digits</span>.<span class="ident">push</span>((<span class="ident">remaining</span> <span class="op">%</span> <span class="ident">radix</span>) <span class="kw">as</span> <span class="ident">u8</span>);
<span class="ident">remaining</span> <span class="op">/</span><span class="op">=</span> <span class="ident">radix</span>;
}
<span class="comment">// Left pad the vec</span>
<span class="ident">digits</span>.<span class="ident">resize</span>(<span class="ident">num_fill_chars</span>, <span class="number">0</span>);
<span class="ident">digits</span>.<span class="ident">reverse</span>();
<span class="ident">digits</span>
}
}
<span class="kw">fn</span> <span class="ident">map_digit</span>(<span class="ident">radix</span>: <span class="ident">u8</span>, <span class="ident">d</span>: <span class="ident">u8</span>) -&gt; <span class="ident">char</span> {
(<span class="kw">match</span> <span class="ident">radix</span> {
<span class="number">10</span> =&gt; <span class="string">b&#39;0&#39;</span> <span class="op">+</span> <span class="ident">d</span>,
<span class="number">16</span> =&gt; {
<span class="kw">if</span> <span class="ident">d</span> <span class="op">&lt;</span> <span class="number">10</span> {
<span class="string">b&#39;0&#39;</span> <span class="op">+</span> <span class="ident">d</span>
} <span class="kw">else</span> {
<span class="string">b&#39;a&#39;</span> <span class="op">+</span> (<span class="ident">d</span> <span class="op">-</span> <span class="number">10</span>)
}
}
<span class="number">26</span> =&gt; <span class="string">b&#39;a&#39;</span> <span class="op">+</span> <span class="ident">d</span>,
<span class="kw">_</span> =&gt; <span class="number">0</span>,
}) <span class="kw">as</span> <span class="ident">char</span>
}
<span class="kw">impl</span> <span class="ident">Display</span> <span class="kw">for</span> <span class="ident">DynamicWidthNumber</span> {
<span class="kw">fn</span> <span class="ident">fmt</span>(<span class="kw-2">&amp;</span><span class="self">self</span>, <span class="ident">f</span>: <span class="kw-2">&amp;mut</span> <span class="ident">Formatter</span>) -&gt; <span class="ident">fmt::Result</span> {
<span class="kw">match</span> <span class="self">self</span>.<span class="ident">radix</span> {
<span class="number">10</span> =&gt; {
<span class="kw">let</span> <span class="ident">num_fill_chars</span> <span class="op">=</span> <span class="self">self</span>.<span class="ident">digits</span>.<span class="ident">len</span>() <span class="op">-</span> <span class="number">2</span>;
<span class="kw">let</span> <span class="ident">digits</span>: <span class="ident">String</span> <span class="op">=</span> <span class="self">self</span>.<span class="ident">digits</span>.<span class="ident">iter</span>().<span class="ident">map</span>(<span class="op">|</span><span class="ident">d</span><span class="op">|</span> (<span class="string">b&#39;0&#39;</span> <span class="op">+</span> <span class="ident">d</span>) <span class="kw">as</span> <span class="ident">char</span>).<span class="ident">collect</span>();
<span class="macro">write!</span>(
<span class="ident">f</span>,
<span class="string">&quot;{empty:9&lt;num_fill_chars$}{digits}&quot;</span>,
<span class="ident">empty</span> <span class="op">=</span> <span class="string">&quot;&quot;</span>,
<span class="ident">num_fill_chars</span> <span class="op">=</span> <span class="ident">num_fill_chars</span>,
<span class="ident">digits</span> <span class="op">=</span> <span class="ident">digits</span>,
)
}
<span class="number">16</span> =&gt; {
<span class="kw">let</span> <span class="ident">num_fill_chars</span> <span class="op">=</span> <span class="self">self</span>.<span class="ident">digits</span>.<span class="ident">len</span>() <span class="op">-</span> <span class="number">2</span>;
<span class="kw">let</span> <span class="ident">digits</span>: <span class="ident">String</span> <span class="op">=</span> <span class="self">self</span>
.<span class="ident">digits</span>
.<span class="ident">iter</span>()
.<span class="ident">map</span>(<span class="op">|</span><span class="ident">d</span><span class="op">|</span> (<span class="kw">if</span> <span class="kw-2">*</span><span class="ident">d</span> <span class="op">&lt;</span> <span class="number">10</span> { <span class="string">b&#39;0&#39;</span> <span class="op">+</span> <span class="ident">d</span> } <span class="kw">else</span> { <span class="string">b&#39;a&#39;</span> <span class="op">+</span> (<span class="ident">d</span> <span class="op">-</span> <span class="number">10</span>) }) <span class="kw">as</span> <span class="ident">char</span>)
.<span class="ident">collect</span>();
<span class="macro">write!</span>(
<span class="ident">f</span>,
<span class="string">&quot;{empty:f&lt;num_fill_chars$}{digits}&quot;</span>,
<span class="ident">empty</span> <span class="op">=</span> <span class="string">&quot;&quot;</span>,
<span class="ident">num_fill_chars</span> <span class="op">=</span> <span class="ident">num_fill_chars</span>,
<span class="ident">digits</span> <span class="op">=</span> <span class="ident">digits</span>,
)
}
<span class="number">26</span> =&gt; {
<span class="kw">let</span> <span class="ident">num_fill_chars</span> <span class="op">=</span> <span class="self">self</span>.<span class="ident">digits</span>.<span class="ident">len</span>() <span class="op">-</span> <span class="number">2</span>;
<span class="kw">let</span> <span class="ident">digits</span>: <span class="ident">String</span> <span class="op">=</span> <span class="self">self</span>.<span class="ident">digits</span>.<span class="ident">iter</span>().<span class="ident">map</span>(<span class="op">|</span><span class="ident">d</span><span class="op">|</span> (<span class="string">b&#39;a&#39;</span> <span class="op">+</span> <span class="ident">d</span>) <span class="kw">as</span> <span class="ident">char</span>).<span class="ident">collect</span>();
<span class="macro">write!</span>(
<span class="ident">f</span>,
<span class="string">&quot;{empty:z&lt;num_fill_chars$}{digits}&quot;</span>,
<span class="ident">empty</span> <span class="op">=</span> <span class="string">&quot;&quot;</span>,
<span class="ident">num_fill_chars</span> <span class="op">=</span> <span class="ident">num_fill_chars</span>,
<span class="ident">digits</span> <span class="op">=</span> <span class="ident">digits</span>,
)
}
<span class="kw">_</span> =&gt; <span class="prelude-val">Err</span>(<span class="ident">fmt::Error</span>),
}
<span class="kw">let</span> <span class="ident">digits</span>: <span class="ident">String</span> <span class="op">=</span> <span class="self">self</span>
.<span class="ident">digits</span>()
.<span class="ident">iter</span>()
.<span class="ident">map</span>(<span class="op">|</span><span class="ident">d</span><span class="op">|</span> <span class="ident">map_digit</span>(<span class="self">self</span>.<span class="ident">radix</span>, <span class="kw-2">*</span><span class="ident">d</span>))
.<span class="ident">collect</span>();
<span class="kw">let</span> <span class="ident">fill</span>: <span class="ident">String</span> <span class="op">=</span> (<span class="number">0</span>..<span class="ident">digits</span>.<span class="ident">len</span>() <span class="op">-</span> <span class="number">2</span>)
.<span class="ident">map</span>(<span class="op">|</span><span class="kw">_</span><span class="op">|</span> <span class="ident">map_digit</span>(<span class="self">self</span>.<span class="ident">radix</span>, <span class="self">self</span>.<span class="ident">radix</span> <span class="op">-</span> <span class="number">1</span>))
.<span class="ident">collect</span>();
<span class="macro">write!</span>(<span class="ident">f</span>, <span class="string">&quot;{fill}{digits}&quot;</span>)
}
}
@@ -990,35 +953,36 @@
<span class="attribute">#[<span class="ident">test</span>]</span>
<span class="kw">fn</span> <span class="ident">test_dynamic_width_number_increment</span>() {
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">n</span> <span class="op">=</span> <span class="ident">Number::DynamicWidth</span>(<span class="ident">DynamicWidthNumber::new</span>(<span class="number">3</span>));
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="kw-2">&amp;</span><span class="macro">vec!</span>[<span class="number">0</span>, <span class="number">0</span>]);
<span class="macro">println!</span>(<span class="string">&quot;Here&quot;</span>);
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">n</span> <span class="op">=</span> <span class="ident">Number::DynamicWidth</span>(<span class="ident">DynamicWidthNumber::new</span>(<span class="number">3</span>, <span class="number">0</span>));
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="macro">vec!</span>[<span class="number">0</span>, <span class="number">0</span>]);
<span class="ident">n</span>.<span class="ident">increment</span>().<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="kw-2">&amp;</span><span class="macro">vec!</span>[<span class="number">0</span>, <span class="number">1</span>]);
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="macro">vec!</span>[<span class="number">0</span>, <span class="number">1</span>]);
<span class="ident">n</span>.<span class="ident">increment</span>().<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="kw-2">&amp;</span><span class="macro">vec!</span>[<span class="number">0</span>, <span class="number">2</span>]);
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="macro">vec!</span>[<span class="number">0</span>, <span class="number">2</span>]);
<span class="ident">n</span>.<span class="ident">increment</span>().<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="kw-2">&amp;</span><span class="macro">vec!</span>[<span class="number">1</span>, <span class="number">0</span>]);
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="macro">vec!</span>[<span class="number">1</span>, <span class="number">0</span>]);
<span class="ident">n</span>.<span class="ident">increment</span>().<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="kw-2">&amp;</span><span class="macro">vec!</span>[<span class="number">1</span>, <span class="number">1</span>]);
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="macro">vec!</span>[<span class="number">1</span>, <span class="number">1</span>]);
<span class="ident">n</span>.<span class="ident">increment</span>().<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="kw-2">&amp;</span><span class="macro">vec!</span>[<span class="number">1</span>, <span class="number">2</span>]);
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="macro">vec!</span>[<span class="number">1</span>, <span class="number">2</span>]);
<span class="ident">n</span>.<span class="ident">increment</span>().<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="kw-2">&amp;</span><span class="macro">vec!</span>[<span class="number">0</span>, <span class="number">0</span>, <span class="number">0</span>]);
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="macro">vec!</span>[<span class="number">0</span>, <span class="number">0</span>, <span class="number">0</span>]);
<span class="ident">n</span>.<span class="ident">increment</span>().<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="kw-2">&amp;</span><span class="macro">vec!</span>[<span class="number">0</span>, <span class="number">0</span>, <span class="number">1</span>]);
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="macro">vec!</span>[<span class="number">0</span>, <span class="number">0</span>, <span class="number">1</span>]);
}
<span class="attribute">#[<span class="ident">test</span>]</span>
<span class="kw">fn</span> <span class="ident">test_dynamic_width_number_display_alphabetic</span>() {
<span class="kw">fn</span> <span class="ident">num</span>(<span class="ident">n</span>: <span class="ident">usize</span>) -&gt; <span class="ident">Number</span> {
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">number</span> <span class="op">=</span> <span class="ident">Number::DynamicWidth</span>(<span class="ident">DynamicWidthNumber::new</span>(<span class="number">26</span>));
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">number</span> <span class="op">=</span> <span class="ident">Number::DynamicWidth</span>(<span class="ident">DynamicWidthNumber::new</span>(<span class="number">26</span>, <span class="number">0</span>));
<span class="kw">for</span> <span class="kw">_</span> <span class="kw">in</span> <span class="number">0</span>..<span class="ident">n</span> {
<span class="ident">number</span>.<span class="ident">increment</span>().<span class="ident">unwrap</span>();
}
@@ -1042,7 +1006,7 @@
<span class="attribute">#[<span class="ident">test</span>]</span>
<span class="kw">fn</span> <span class="ident">test_dynamic_width_number_display_numeric_decimal</span>() {
<span class="kw">fn</span> <span class="ident">num</span>(<span class="ident">n</span>: <span class="ident">usize</span>) -&gt; <span class="ident">Number</span> {
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">number</span> <span class="op">=</span> <span class="ident">Number::DynamicWidth</span>(<span class="ident">DynamicWidthNumber::new</span>(<span class="number">10</span>));
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">number</span> <span class="op">=</span> <span class="ident">Number::DynamicWidth</span>(<span class="ident">DynamicWidthNumber::new</span>(<span class="number">10</span>, <span class="number">0</span>));
<span class="kw">for</span> <span class="kw">_</span> <span class="kw">in</span> <span class="number">0</span>..<span class="ident">n</span> {
<span class="ident">number</span>.<span class="ident">increment</span>().<span class="ident">unwrap</span>();
}
@@ -1063,7 +1027,7 @@
<span class="attribute">#[<span class="ident">test</span>]</span>
<span class="kw">fn</span> <span class="ident">test_dynamic_width_number_display_numeric_hexadecimal</span>() {
<span class="kw">fn</span> <span class="ident">num</span>(<span class="ident">n</span>: <span class="ident">usize</span>) -&gt; <span class="ident">Number</span> {
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">number</span> <span class="op">=</span> <span class="ident">Number::DynamicWidth</span>(<span class="ident">DynamicWidthNumber::new</span>(<span class="number">16</span>));
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">number</span> <span class="op">=</span> <span class="ident">Number::DynamicWidth</span>(<span class="ident">DynamicWidthNumber::new</span>(<span class="number">16</span>, <span class="number">0</span>));
<span class="kw">for</span> <span class="kw">_</span> <span class="kw">in</span> <span class="number">0</span>..<span class="ident">n</span> {
<span class="ident">number</span>.<span class="ident">increment</span>().<span class="ident">unwrap</span>();
}
@@ -1086,31 +1050,31 @@
<span class="attribute">#[<span class="ident">test</span>]</span>
<span class="kw">fn</span> <span class="ident">test_fixed_width_number_increment</span>() {
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">n</span> <span class="op">=</span> <span class="ident">Number::FixedWidth</span>(<span class="ident">FixedWidthNumber::new</span>(<span class="number">3</span>, <span class="number">2</span>));
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="kw-2">&amp;</span><span class="macro">vec!</span>[<span class="number">0</span>, <span class="number">0</span>]);
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">n</span> <span class="op">=</span> <span class="ident">Number::FixedWidth</span>(<span class="ident">FixedWidthNumber::new</span>(<span class="number">3</span>, <span class="number">2</span>, <span class="number">0</span>).<span class="ident">unwrap</span>());
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="macro">vec!</span>[<span class="number">0</span>, <span class="number">0</span>]);
<span class="ident">n</span>.<span class="ident">increment</span>().<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="kw-2">&amp;</span><span class="macro">vec!</span>[<span class="number">0</span>, <span class="number">1</span>]);
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="macro">vec!</span>[<span class="number">0</span>, <span class="number">1</span>]);
<span class="ident">n</span>.<span class="ident">increment</span>().<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="kw-2">&amp;</span><span class="macro">vec!</span>[<span class="number">0</span>, <span class="number">2</span>]);
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="macro">vec!</span>[<span class="number">0</span>, <span class="number">2</span>]);
<span class="ident">n</span>.<span class="ident">increment</span>().<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="kw-2">&amp;</span><span class="macro">vec!</span>[<span class="number">1</span>, <span class="number">0</span>]);
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="macro">vec!</span>[<span class="number">1</span>, <span class="number">0</span>]);
<span class="ident">n</span>.<span class="ident">increment</span>().<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="kw-2">&amp;</span><span class="macro">vec!</span>[<span class="number">1</span>, <span class="number">1</span>]);
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="macro">vec!</span>[<span class="number">1</span>, <span class="number">1</span>]);
<span class="ident">n</span>.<span class="ident">increment</span>().<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="kw-2">&amp;</span><span class="macro">vec!</span>[<span class="number">1</span>, <span class="number">2</span>]);
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="macro">vec!</span>[<span class="number">1</span>, <span class="number">2</span>]);
<span class="ident">n</span>.<span class="ident">increment</span>().<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="kw-2">&amp;</span><span class="macro">vec!</span>[<span class="number">2</span>, <span class="number">0</span>]);
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="macro">vec!</span>[<span class="number">2</span>, <span class="number">0</span>]);
<span class="ident">n</span>.<span class="ident">increment</span>().<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="kw-2">&amp;</span><span class="macro">vec!</span>[<span class="number">2</span>, <span class="number">1</span>]);
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="macro">vec!</span>[<span class="number">2</span>, <span class="number">1</span>]);
<span class="ident">n</span>.<span class="ident">increment</span>().<span class="ident">unwrap</span>();
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="kw-2">&amp;</span><span class="macro">vec!</span>[<span class="number">2</span>, <span class="number">2</span>]);
<span class="macro">assert_eq!</span>(<span class="ident">n</span>.<span class="ident">digits</span>(), <span class="macro">vec!</span>[<span class="number">2</span>, <span class="number">2</span>]);
<span class="macro">assert!</span>(<span class="ident">n</span>.<span class="ident">increment</span>().<span class="ident">is_err</span>());
}
<span class="attribute">#[<span class="ident">test</span>]</span>
<span class="kw">fn</span> <span class="ident">test_fixed_width_number_display_alphabetic</span>() {
<span class="kw">fn</span> <span class="ident">num</span>(<span class="ident">n</span>: <span class="ident">usize</span>) -&gt; <span class="prelude-ty">Result</span><span class="op">&lt;</span><span class="ident">Number</span>, <span class="ident">Overflow</span><span class="op">&gt;</span> {
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">number</span> <span class="op">=</span> <span class="ident">Number::FixedWidth</span>(<span class="ident">FixedWidthNumber::new</span>(<span class="number">26</span>, <span class="number">2</span>));
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">number</span> <span class="op">=</span> <span class="ident">Number::FixedWidth</span>(<span class="ident">FixedWidthNumber::new</span>(<span class="number">26</span>, <span class="number">2</span>, <span class="number">0</span>).<span class="ident">unwrap</span>());
<span class="kw">for</span> <span class="kw">_</span> <span class="kw">in</span> <span class="number">0</span>..<span class="ident">n</span> {
<span class="ident">number</span>.<span class="ident">increment</span>()<span class="question-mark">?</span>;
}
@@ -1135,7 +1099,7 @@
<span class="attribute">#[<span class="ident">test</span>]</span>
<span class="kw">fn</span> <span class="ident">test_fixed_width_number_display_numeric_decimal</span>() {
<span class="kw">fn</span> <span class="ident">num</span>(<span class="ident">n</span>: <span class="ident">usize</span>) -&gt; <span class="prelude-ty">Result</span><span class="op">&lt;</span><span class="ident">Number</span>, <span class="ident">Overflow</span><span class="op">&gt;</span> {
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">number</span> <span class="op">=</span> <span class="ident">Number::FixedWidth</span>(<span class="ident">FixedWidthNumber::new</span>(<span class="number">10</span>, <span class="number">2</span>));
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">number</span> <span class="op">=</span> <span class="ident">Number::FixedWidth</span>(<span class="ident">FixedWidthNumber::new</span>(<span class="number">10</span>, <span class="number">2</span>, <span class="number">0</span>).<span class="ident">unwrap</span>());
<span class="kw">for</span> <span class="kw">_</span> <span class="kw">in</span> <span class="number">0</span>..<span class="ident">n</span> {
<span class="ident">number</span>.<span class="ident">increment</span>()<span class="question-mark">?</span>;
}
@@ -1154,7 +1118,7 @@
<span class="attribute">#[<span class="ident">test</span>]</span>
<span class="kw">fn</span> <span class="ident">test_fixed_width_number_display_numeric_hexadecimal</span>() {
<span class="kw">fn</span> <span class="ident">num</span>(<span class="ident">n</span>: <span class="ident">usize</span>) -&gt; <span class="prelude-ty">Result</span><span class="op">&lt;</span><span class="ident">Number</span>, <span class="ident">Overflow</span><span class="op">&gt;</span> {
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">number</span> <span class="op">=</span> <span class="ident">Number::FixedWidth</span>(<span class="ident">FixedWidthNumber::new</span>(<span class="number">16</span>, <span class="number">2</span>));
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">number</span> <span class="op">=</span> <span class="ident">Number::FixedWidth</span>(<span class="ident">FixedWidthNumber::new</span>(<span class="number">16</span>, <span class="number">2</span>, <span class="number">0</span>).<span class="ident">unwrap</span>());
<span class="kw">for</span> <span class="kw">_</span> <span class="kw">in</span> <span class="number">0</span>..<span class="ident">n</span> {
<span class="ident">number</span>.<span class="ident">increment</span>()<span class="question-mark">?</span>;
}
@@ -1169,6 +1133,34 @@
<span class="macro">assert_eq!</span>(<span class="macro">format!</span>(<span class="string">&quot;{}&quot;</span>, <span class="ident">num</span>(<span class="number">16</span> <span class="op">*</span> <span class="number">16</span> <span class="op">-</span> <span class="number">1</span>).<span class="ident">unwrap</span>()), <span class="string">&quot;ff&quot;</span>);
<span class="macro">assert!</span>(<span class="ident">num</span>(<span class="number">16</span> <span class="op">*</span> <span class="number">16</span>).<span class="ident">is_err</span>());
}
<span class="attribute">#[<span class="ident">test</span>]</span>
<span class="kw">fn</span> <span class="ident">test_fixed_width_number_start_suffix</span>() {
<span class="kw">fn</span> <span class="ident">num</span>(<span class="ident">n</span>: <span class="ident">usize</span>) -&gt; <span class="prelude-ty">Result</span><span class="op">&lt;</span><span class="ident">Number</span>, <span class="ident">Overflow</span><span class="op">&gt;</span> {
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">number</span> <span class="op">=</span> <span class="ident">Number::FixedWidth</span>(<span class="ident">FixedWidthNumber::new</span>(<span class="number">16</span>, <span class="number">2</span>, <span class="number">0x14</span>)<span class="question-mark">?</span>);
<span class="kw">for</span> <span class="kw">_</span> <span class="kw">in</span> <span class="number">0</span>..<span class="ident">n</span> {
<span class="ident">number</span>.<span class="ident">increment</span>()<span class="question-mark">?</span>;
}
<span class="prelude-val">Ok</span>(<span class="ident">number</span>)
}
<span class="macro">assert_eq!</span>(<span class="macro">format!</span>(<span class="string">&quot;{}&quot;</span>, <span class="ident">num</span>(<span class="number">0</span>).<span class="ident">unwrap</span>()), <span class="string">&quot;14&quot;</span>);
<span class="macro">assert_eq!</span>(<span class="macro">format!</span>(<span class="string">&quot;{}&quot;</span>, <span class="ident">num</span>(<span class="number">0xf</span>).<span class="ident">unwrap</span>()), <span class="string">&quot;23&quot;</span>);
}
<span class="attribute">#[<span class="ident">test</span>]</span>
<span class="kw">fn</span> <span class="ident">test_dynamic_width_number_start_suffix</span>() {
<span class="kw">fn</span> <span class="ident">num</span>(<span class="ident">n</span>: <span class="ident">usize</span>) -&gt; <span class="prelude-ty">Result</span><span class="op">&lt;</span><span class="ident">Number</span>, <span class="ident">Overflow</span><span class="op">&gt;</span> {
<span class="kw">let</span> <span class="kw-2">mut</span> <span class="ident">number</span> <span class="op">=</span> <span class="ident">Number::DynamicWidth</span>(<span class="ident">DynamicWidthNumber::new</span>(<span class="number">10</span>, <span class="number">8</span>));
<span class="kw">for</span> <span class="kw">_</span> <span class="kw">in</span> <span class="number">0</span>..<span class="ident">n</span> {
<span class="ident">number</span>.<span class="ident">increment</span>()<span class="question-mark">?</span>;
}
<span class="prelude-val">Ok</span>(<span class="ident">number</span>)
}
<span class="macro">assert_eq!</span>(<span class="macro">format!</span>(<span class="string">&quot;{}&quot;</span>, <span class="ident">num</span>(<span class="number">0</span>).<span class="ident">unwrap</span>()), <span class="string">&quot;08&quot;</span>);
<span class="macro">assert_eq!</span>(<span class="macro">format!</span>(<span class="string">&quot;{}&quot;</span>, <span class="ident">num</span>(<span class="number">8</span>).<span class="ident">unwrap</span>()), <span class="string">&quot;16&quot;</span>);
}
}
</code></pre></div>
</section></div></main><div id="rustdoc-vars" data-root-path="../../" data-current-crate="uu_split" data-themes="ayu,dark,light" data-resource-suffix="" data-rustdoc-version="1.64.0 (a55dd71d5 2022-09-19)" ></div></body></html>
+45 -11
View File
@@ -1365,6 +1365,23 @@
<span id="1365">1365</span>
<span id="1366">1366</span>
<span id="1367">1367</span>
<span id="1368">1368</span>
<span id="1369">1369</span>
<span id="1370">1370</span>
<span id="1371">1371</span>
<span id="1372">1372</span>
<span id="1373">1373</span>
<span id="1374">1374</span>
<span id="1375">1375</span>
<span id="1376">1376</span>
<span id="1377">1377</span>
<span id="1378">1378</span>
<span id="1379">1379</span>
<span id="1380">1380</span>
<span id="1381">1381</span>
<span id="1382">1382</span>
<span id="1383">1383</span>
<span id="1384">1384</span>
</pre><pre class="rust"><code><span class="comment">// * This file is part of the uutils coreutils package.</span>
<span class="comment">// *</span>
<span class="comment">// * (c) Akira Hayakawa &lt;ruby.wktk@gmail.com&gt;</span>
@@ -1511,7 +1528,7 @@
.<span class="ident">takes_value</span>(<span class="bool-val">true</span>)
.<span class="ident">value_name</span>(<span class="string">&quot;N&quot;</span>)
.<span class="ident">default_value</span>(<span class="ident">OPT_DEFAULT_SUFFIX_LENGTH</span>)
.<span class="ident">help</span>(<span class="string">&quot;use suffixes of length N (default 2)&quot;</span>),
.<span class="ident">help</span>(<span class="string">&quot;use suffixes of fixed length N. 0 implies dynamic length.&quot;</span>),
)
.<span class="ident">arg</span>(
<span class="ident">Arg::new</span>(<span class="ident">OPT_HEX_SUFFIXES</span>)
@@ -1767,13 +1784,23 @@
}
<span class="doccomment">/// Parse the suffix type from the command-line arguments.</span>
<span class="kw">fn</span> <span class="ident">suffix_type_from</span>(<span class="ident">matches</span>: <span class="kw-2">&amp;</span><span class="ident">ArgMatches</span>) -&gt; <span class="ident">SuffixType</span> {
<span class="kw">fn</span> <span class="ident">suffix_type_from</span>(<span class="ident">matches</span>: <span class="kw-2">&amp;</span><span class="ident">ArgMatches</span>) -&gt; <span class="prelude-ty">Result</span><span class="op">&lt;</span>(<span class="ident">SuffixType</span>, <span class="ident">usize</span>), <span class="ident">SettingsError</span><span class="op">&gt;</span> {
<span class="kw">if</span> <span class="ident">matches</span>.<span class="ident">value_source</span>(<span class="ident">OPT_NUMERIC_SUFFIXES</span>) <span class="op">==</span> <span class="prelude-val">Some</span>(<span class="ident">ValueSource::CommandLine</span>) {
<span class="ident">SuffixType::Decimal</span>
<span class="kw">let</span> <span class="ident">suffix_start</span> <span class="op">=</span> <span class="ident">matches</span>.<span class="ident">value_of</span>(<span class="ident">OPT_NUMERIC_SUFFIXES</span>);
<span class="kw">let</span> <span class="ident">suffix_start</span> <span class="op">=</span> <span class="ident">suffix_start</span>.<span class="ident">ok_or</span>(<span class="ident">SettingsError::SuffixNotParsable</span>(<span class="ident">String::new</span>()))<span class="question-mark">?</span>;
<span class="kw">let</span> <span class="ident">suffix_start</span> <span class="op">=</span> <span class="ident">suffix_start</span>
.<span class="ident">parse</span>()
.<span class="ident">map_err</span>(<span class="op">|</span><span class="kw">_</span><span class="op">|</span> <span class="ident">SettingsError::SuffixNotParsable</span>(<span class="ident">suffix_start</span>.<span class="ident">to_string</span>()))<span class="question-mark">?</span>;
<span class="prelude-val">Ok</span>((<span class="ident">SuffixType::Decimal</span>, <span class="ident">suffix_start</span>))
} <span class="kw">else</span> <span class="kw">if</span> <span class="ident">matches</span>.<span class="ident">value_source</span>(<span class="ident">OPT_HEX_SUFFIXES</span>) <span class="op">==</span> <span class="prelude-val">Some</span>(<span class="ident">ValueSource::CommandLine</span>) {
<span class="ident">SuffixType::Hexadecimal</span>
<span class="kw">let</span> <span class="ident">suffix_start</span> <span class="op">=</span> <span class="ident">matches</span>.<span class="ident">value_of</span>(<span class="ident">OPT_HEX_SUFFIXES</span>);
<span class="kw">let</span> <span class="ident">suffix_start</span> <span class="op">=</span> <span class="ident">suffix_start</span>.<span class="ident">ok_or</span>(<span class="ident">SettingsError::SuffixNotParsable</span>(<span class="ident">String::new</span>()))<span class="question-mark">?</span>;
<span class="kw">let</span> <span class="ident">suffix_start</span> <span class="op">=</span> <span class="ident">usize::from_str_radix</span>(<span class="ident">suffix_start</span>, <span class="number">16</span>)
.<span class="ident">map_err</span>(<span class="op">|</span><span class="kw">_</span><span class="op">|</span> <span class="ident">SettingsError::SuffixNotParsable</span>(<span class="ident">suffix_start</span>.<span class="ident">to_string</span>()))<span class="question-mark">?</span>;
<span class="prelude-val">Ok</span>((<span class="ident">SuffixType::Hexadecimal</span>, <span class="ident">suffix_start</span>))
} <span class="kw">else</span> {
<span class="ident">SuffixType::Alphabetic</span>
<span class="comment">// no numeric/hex suffix</span>
<span class="prelude-val">Ok</span>((<span class="ident">SuffixType::Alphabetic</span>, <span class="number">0</span>))
}
}
@@ -1785,6 +1812,7 @@
<span class="ident">prefix</span>: <span class="ident">String</span>,
<span class="ident">suffix_type</span>: <span class="ident">SuffixType</span>,
<span class="ident">suffix_length</span>: <span class="ident">usize</span>,
<span class="ident">suffix_start</span>: <span class="ident">usize</span>,
<span class="ident">additional_suffix</span>: <span class="ident">String</span>,
<span class="ident">input</span>: <span class="ident">String</span>,
<span class="doccomment">/// When supplied, a shell command to output to instead of xaa, xab …</span>
@@ -1864,7 +1892,7 @@
<span class="kw">return</span> <span class="prelude-val">Err</span>(<span class="ident">SettingsError::SuffixContainsSeparator</span>(<span class="ident">additional_suffix</span>));
}
<span class="kw">let</span> <span class="ident">strategy</span> <span class="op">=</span> <span class="ident">Strategy::from</span>(<span class="ident">matches</span>).<span class="ident">map_err</span>(<span class="ident">SettingsError::Strategy</span>)<span class="question-mark">?</span>;
<span class="kw">let</span> <span class="ident">suffix_type</span> <span class="op">=</span> <span class="ident">suffix_type_from</span>(<span class="ident">matches</span>);
<span class="kw">let</span> (<span class="ident">suffix_type</span>, <span class="ident">suffix_start</span>) <span class="op">=</span> <span class="ident">suffix_type_from</span>(<span class="ident">matches</span>)<span class="question-mark">?</span>;
<span class="kw">let</span> <span class="ident">suffix_length_str</span> <span class="op">=</span> <span class="ident">matches</span>.<span class="ident">get_one</span>::<span class="op">&lt;</span><span class="ident">String</span><span class="op">&gt;</span>(<span class="ident">OPT_SUFFIX_LENGTH</span>).<span class="ident">unwrap</span>();
<span class="kw">let</span> <span class="ident">suffix_length</span>: <span class="ident">usize</span> <span class="op">=</span> <span class="ident">suffix_length_str</span>
.<span class="ident">parse</span>()
@@ -1884,6 +1912,7 @@
.<span class="ident">parse</span>()
.<span class="ident">map_err</span>(<span class="op">|</span><span class="kw">_</span><span class="op">|</span> <span class="ident">SettingsError::SuffixNotParsable</span>(<span class="ident">suffix_length_str</span>.<span class="ident">to_string</span>()))<span class="question-mark">?</span>,
<span class="ident">suffix_type</span>,
<span class="ident">suffix_start</span>,
<span class="ident">additional_suffix</span>,
<span class="ident">verbose</span>: <span class="ident">matches</span>.<span class="ident">value_source</span>(<span class="string">&quot;verbose&quot;</span>) <span class="op">==</span> <span class="prelude-val">Some</span>(<span class="ident">ValueSource::CommandLine</span>),
<span class="ident">strategy</span>,
@@ -1956,7 +1985,8 @@
<span class="kw-2">&amp;</span><span class="ident">settings</span>.<span class="ident">additional_suffix</span>,
<span class="ident">settings</span>.<span class="ident">suffix_length</span>,
<span class="ident">settings</span>.<span class="ident">suffix_type</span>,
);
<span class="ident">settings</span>.<span class="ident">suffix_start</span>,
)<span class="question-mark">?</span>;
<span class="kw">let</span> <span class="ident">filename</span> <span class="op">=</span> <span class="ident">filename_iterator</span>
.<span class="ident">next</span>()
.<span class="ident">ok_or_else</span>(<span class="op">|</span><span class="op">|</span> <span class="ident">USimpleError::new</span>(<span class="number">1</span>, <span class="string">&quot;output file suffixes exhausted&quot;</span>))<span class="question-mark">?</span>;
@@ -2084,7 +2114,8 @@
<span class="kw-2">&amp;</span><span class="ident">settings</span>.<span class="ident">additional_suffix</span>,
<span class="ident">settings</span>.<span class="ident">suffix_length</span>,
<span class="ident">settings</span>.<span class="ident">suffix_type</span>,
);
<span class="ident">settings</span>.<span class="ident">suffix_start</span>,
)<span class="question-mark">?</span>;
<span class="kw">let</span> <span class="ident">filename</span> <span class="op">=</span> <span class="ident">filename_iterator</span>
.<span class="ident">next</span>()
.<span class="ident">ok_or_else</span>(<span class="op">|</span><span class="op">|</span> <span class="ident">USimpleError::new</span>(<span class="number">1</span>, <span class="string">&quot;output file suffixes exhausted&quot;</span>))<span class="question-mark">?</span>;
@@ -2192,7 +2223,8 @@
<span class="kw-2">&amp;</span><span class="ident">settings</span>.<span class="ident">additional_suffix</span>,
<span class="ident">settings</span>.<span class="ident">suffix_length</span>,
<span class="ident">settings</span>.<span class="ident">suffix_type</span>,
);
<span class="ident">settings</span>.<span class="ident">suffix_start</span>,
)<span class="question-mark">?</span>;
<span class="kw">let</span> <span class="ident">filename</span> <span class="op">=</span> <span class="ident">filename_iterator</span>
.<span class="ident">next</span>()
.<span class="ident">ok_or_else</span>(<span class="op">|</span><span class="op">|</span> <span class="ident">USimpleError::new</span>(<span class="number">1</span>, <span class="string">&quot;output file suffixes exhausted&quot;</span>))<span class="question-mark">?</span>;
@@ -2389,7 +2421,8 @@
<span class="kw-2">&amp;</span><span class="ident">settings</span>.<span class="ident">additional_suffix</span>,
<span class="ident">settings</span>.<span class="ident">suffix_length</span>,
<span class="ident">settings</span>.<span class="ident">suffix_type</span>,
);
<span class="ident">settings</span>.<span class="ident">suffix_start</span>,
)<span class="question-mark">?</span>;
<span class="comment">// Create one writer for each chunk. This will create each</span>
<span class="comment">// of the underlying files (if not in `--filter` mode).</span>
@@ -2465,7 +2498,8 @@
<span class="kw-2">&amp;</span><span class="ident">settings</span>.<span class="ident">additional_suffix</span>,
<span class="ident">settings</span>.<span class="ident">suffix_length</span>,
<span class="ident">settings</span>.<span class="ident">suffix_type</span>,
);
<span class="ident">settings</span>.<span class="ident">suffix_start</span>,
)<span class="question-mark">?</span>;
<span class="comment">// Create one writer for each chunk. This will create each</span>
<span class="comment">// of the underlying files (if not in `--filter` mode).</span>
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long

Some files were not shown because too many files have changed in this diff Show More