From 0f4e3dff08673e9082434e85194a1b342ce2853d Mon Sep 17 00:00:00 2001 From: Jethro Beekman Date: Tue, 30 Mar 2021 17:56:22 +0200 Subject: [PATCH] Update to 2021-03-25 --- Cargo.toml | 2 +- build-src.sh | 10 +- build.rs | 2 +- edit-patches.sh | 1 + functions.sh | 14 +- mapping.rs | 628 +++++ ...4bf532ceec915f74460daf5344bb8ccf23d3.patch | 1862 +++++++++++++++ ...d309dcbaa8425c702d1439592b87fff0a69e.patch | 1761 ++++++++++++++ ...789014f9aef9ffac7d7d1e22fa72c7b85ab7.patch | 2002 ++++++++++++++++ ...7faacb7c33eaad6614f62a7d560b0d2660a5.patch | 1888 +++++++++++++++ ...904dfaf5e75fbcc1305c8b0aad5fae71a4ff.patch | 1862 +++++++++++++++ ...bd01dfae488392dc6f08daa2d0d8d370fb00.patch | 1903 +++++++++++++++ ...918c75b05d065ce3bf98b20d62465b5afc55.patch | 1986 ++++++++++++++++ ...6106b7955d3dcde26719b9b62a5a2c4b78fe.patch | 1797 ++++++++++++++ ...30519ca1c020623a550dc6b250eacea68e72.patch | 2068 ++++++++++++++++ ...eb4c3c00b7831226cf5266aacb5fca1e13f3.patch | 2078 ++++++++++++++++ ...14da942f281bc2dc3b14b629d3e660b3484f.patch | 1830 ++++++++++++++ ...54e9c930c4ff015e1958ad1c640deffd29b2.patch | 1850 +++++++++++++++ ...b45ae878b821975c4ebd94cc1e49f6073fd0.patch | 1891 +++++++++++++++ ...ea38b045624dc8b42ec948fc169eaff1206a.patch | 2002 ++++++++++++++++ ...28e7138d8753487ed8895ce0f5f2e643ffad.patch | 1817 ++++++++++++++ ...9a9ead550551e879af64ba91a0316da1c422.patch | 1987 ++++++++++++++++ ...f59893f4dc249f06047dca659b5b2172063f.patch | 1893 +++++++++++++++ ...2225dd06ab06ef75ef97841c66c7d9b6e56c.patch | 1850 +++++++++++++++ ...d6003b3eb15168421084a27223596517899c.patch | 1893 +++++++++++++++ ...50665601a8abe8935f7b55d5732fe4c4224f.patch | 2078 ++++++++++++++++ ...b57c0210ecbe92298c53ec4e1e39f97e4e4c.patch | 1797 ++++++++++++++ ...c9d35498e7ae3da261f6141d6d73b915e1e8.patch | 1817 ++++++++++++++ ...a88b7a1e68326d092b9cbbbbdd616a51077f.patch | 1832 +++++++++++++++ ...d52d7710dcad5fec0cd731b836b02ba4a8f4.patch | 1893 +++++++++++++++ ...ed3af19e604d7b65e130145fcecdc69fba7a.patch | 2010 ++++++++++++++++ ...511fbc1f9a0c7340f7f0d037aa4dd13a588f.patch | 1893 +++++++++++++++ ...88fa46e04cd5faf53d369a1a640a97e2bb08.patch | 1958 +++++++++++++++ ...385615c61f6c9d63dccfb3548812f1ba1320.patch | 1872 +++++++++++++++ ...7f198fa56943a2837583d555896badb5733d.patch | 1957 +++++++++++++++ ...96ad65db877c2f140dfc7a25f3fc6f2e40c6.patch | 1797 ++++++++++++++ ...e1c4e6b214916de690ee25c17f862e166a28.patch | 1888 +++++++++++++++ ...154886039ddbd7c1b8bf4cc273b774b14ec7.patch | 1850 +++++++++++++++ ...0353bf9cc415f4554a9b4851c14e4255329f.patch | 1848 +++++++++++++++ ...c135d185e8492e8a2b9db5ca04e51c3293fa.patch | 1893 +++++++++++++++ ...6b42b5ed342d30c539e22810c26d312995e2.patch | 1797 ++++++++++++++ ...f79da3f72269e6fe7aac1355df1420613889.patch | 1911 +++++++++++++++ ...934a154abac9a2af72c55e4c08277172e087.patch | 2082 ++++++++++++++++ ...81bacc78a00a63766f12a17560701ab5c1e8.patch | 1891 +++++++++++++++ ...a496cc8ce261e87abbd998b36ab16dab4f4b.patch | 1850 +++++++++++++++ ...7ef59cd0eb95b50d0cde14b05e0079b3ebe9.patch | 1830 ++++++++++++++ ...33b304424ae63dc70e10c6676dd645230f94.patch | 1964 ++++++++++++++++ ...94632ec6160c3d2cfaad777c16a27ce08609.patch | 1891 +++++++++++++++ ...3abfb1aa3a38e0b3b3508c760fc8e712226c.patch | 1891 +++++++++++++++ ...ba112429eb9bc0b99a6fe32a453c920a764c.patch | 1848 +++++++++++++++ ...f6751c5726d884440d4e8d462a9ee6c5efc1.patch | 2091 ++++++++++++++++ ...0aca2086e5c4dca5aae9a92a065a9ff4ac56.patch | 1848 +++++++++++++++ ...fb0f7396ceb1ca18cd82ca3deb795f5e60b2.patch | 2060 ++++++++++++++++ ...65fde3f92a84218fc338de6ab967fafd1820.patch | 2002 ++++++++++++++++ ...0b57968fd875c2d9ce50446868b906f54752.patch | 1893 +++++++++++++++ ...e3bbb2da2f5eb5f4a95efd6846e9ea93a160.patch | 1958 +++++++++++++++ ...35f7b6cb4232be5ac4cc031202c7ad82260b.patch | 1817 ++++++++++++++ ...746a327320048ae2b212f34edcadbcafcadf.patch | 2060 ++++++++++++++++ ...a50e04460fff646830502d575b82dbf17055.patch | 1832 +++++++++++++++ ...51ae49289ce6f693ca0dabf4c9c15164f67d.patch | 1903 +++++++++++++++ ...2752d855722c55dbc71d9b22bd42eabfc468.patch | 1761 ++++++++++++++ ...62fa0a59d0ba620889f97513929a113a6fbd.patch | 2093 +++++++++++++++++ ...9fe451c37ec192b282ec7303b9809b49df93.patch | 1891 +++++++++++++++ ...f90b06c9bf2bfa2c2f4aedd7c395cb92195d.patch | 1797 ++++++++++++++ ...95bbca73be761402585ead491111163c44d6.patch | 2084 ++++++++++++++++ ...3dc478ba13f405cf9a877a4894de096a1cc1.patch | 1797 ++++++++++++++ ...d272af149c4126f90a0262d796d7401ba7a1.patch | 1848 +++++++++++++++ ...aa2d0301c5fc448299501278ae2db4e15e50.patch | 1761 ++++++++++++++ ...552167d2651ceb13437f9fde4dca95045912.patch | 2002 ++++++++++++++++ ...59cc41f8eeb36ee269cae3275d7620189c14.patch | 1761 ++++++++++++++ ...69eef8c1d747e82694547fd57a1400a5afec.patch | 2078 ++++++++++++++++ ...76cfde64d06bb93c1f9102a0312d84cd0983.patch | 1986 ++++++++++++++++ ...8bbd6d0e7bbfa2891934a1af2934cab3b6bb.patch | 2078 ++++++++++++++++ ...8600ef3c5e795c4133cfd91a1df088f2252e.patch | 1761 ++++++++++++++ ...0dceee2cb6b882b26ec6e294560e51ef0853.patch | 1848 +++++++++++++++ ...e6a53aef5cd1b939ecfa18f56bdf5bf0451c.patch | 1910 +++++++++++++++ ...709405270cae2dfdf99d9a8d57a4f672ad34.patch | 2010 ++++++++++++++++ ...ae54e680c0b28e8311459cb8fd11315485a0.patch | 2060 ++++++++++++++++ ...2c1e4f8fa6bd49fe9c395353f9e24c7b51fc.patch | 1888 +++++++++++++++ ...4a33f53689bc0847775669a14f666a138fd7.patch | 1903 +++++++++++++++ ...6c39474377c7d47e261b380d0be3aed104cc.patch | 1797 ++++++++++++++ ...e11e9fcbd76c0a2dc47211dcd654effed010.patch | 1891 +++++++++++++++ ...97c4cbcb160b3754c803284dd0110d1de1e4.patch | 2084 ++++++++++++++++ ...07223346b06da723c25a3ac42f874e6c945c.patch | 1832 +++++++++++++++ ...7fca40d129435c53a69c6662d7bfac29771d.patch | 1910 +++++++++++++++ ...9f383848dcb31a2f94bb1df5270ea21aff4b.patch | 1848 +++++++++++++++ ...ffbbcb41559c8de3ca3b94f3b9467e662a19.patch | 1797 ++++++++++++++ ...e5e21d8aa61e00124f634a71325e6d3bfaa8.patch | 2078 ++++++++++++++++ ...26cc2e0b3a800836bcf8733dee0924f6b7ab.patch | 1888 +++++++++++++++ ...6c7c809eba2a4eed5e281f19ab7331998c6f.patch | 1872 +++++++++++++++ ...214b29cd7de06dd10f673986d38e568b077c.patch | 1797 ++++++++++++++ ...c8abda7cb8e8693aa876fbd1e21f2a6a5c2d.patch | 2078 ++++++++++++++++ ...6d28d1c2f8340ab5b99df4bdb15aa232f3f3.patch | 1817 ++++++++++++++ ...a5624dff1d96249080fe365ed794431f45db.patch | 1888 +++++++++++++++ ...22fead6249671cbcb090b24bce58fab38de0.patch | 1888 +++++++++++++++ src/lib.rs | 22 +- 96 files changed, 170458 insertions(+), 25 deletions(-) create mode 100644 patches/03c64bf532ceec915f74460daf5344bb8ccf23d3.patch create mode 100644 patches/04f0d309dcbaa8425c702d1439592b87fff0a69e.patch create mode 100644 patches/0506789014f9aef9ffac7d7d1e22fa72c7b85ab7.patch create mode 100644 patches/05fc7faacb7c33eaad6614f62a7d560b0d2660a5.patch create mode 100644 patches/08f2904dfaf5e75fbcc1305c8b0aad5fae71a4ff.patch create mode 100644 patches/0af3bd01dfae488392dc6f08daa2d0d8d370fb00.patch create mode 100644 patches/11ce918c75b05d065ce3bf98b20d62465b5afc55.patch create mode 100644 patches/1b946106b7955d3dcde26719b9b62a5a2c4b78fe.patch create mode 100644 patches/1bf130519ca1c020623a550dc6b250eacea68e72.patch create mode 100644 patches/250eeb4c3c00b7831226cf5266aacb5fca1e13f3.patch create mode 100644 patches/260514da942f281bc2dc3b14b629d3e660b3484f.patch create mode 100644 patches/276b54e9c930c4ff015e1958ad1c640deffd29b2.patch create mode 100644 patches/2c31b45ae878b821975c4ebd94cc1e49f6073fd0.patch create mode 100644 patches/2c56ea38b045624dc8b42ec948fc169eaff1206a.patch create mode 100644 patches/2fee28e7138d8753487ed8895ce0f5f2e643ffad.patch create mode 100644 patches/30e49a9ead550551e879af64ba91a0316da1c422.patch create mode 100644 patches/353df59893f4dc249f06047dca659b5b2172063f.patch create mode 100644 patches/39c52225dd06ab06ef75ef97841c66c7d9b6e56c.patch create mode 100644 patches/3cecd6003b3eb15168421084a27223596517899c.patch create mode 100644 patches/410550665601a8abe8935f7b55d5732fe4c4224f.patch create mode 100644 patches/413ab57c0210ecbe92298c53ec4e1e39f97e4e4c.patch create mode 100644 patches/4436c9d35498e7ae3da261f6141d6d73b915e1e8.patch create mode 100644 patches/4646a88b7a1e68326d092b9cbbbbdd616a51077f.patch create mode 100644 patches/471dd52d7710dcad5fec0cd731b836b02ba4a8f4.patch create mode 100644 patches/4e27ed3af19e604d7b65e130145fcecdc69fba7a.patch create mode 100644 patches/5304511fbc1f9a0c7340f7f0d037aa4dd13a588f.patch create mode 100644 patches/56d288fa46e04cd5faf53d369a1a640a97e2bb08.patch create mode 100644 patches/5768385615c61f6c9d63dccfb3548812f1ba1320.patch create mode 100644 patches/5acb7f198fa56943a2837583d555896badb5733d.patch create mode 100644 patches/5b5196ad65db877c2f140dfc7a25f3fc6f2e40c6.patch create mode 100644 patches/5d8fe1c4e6b214916de690ee25c17f862e166a28.patch create mode 100644 patches/5d90154886039ddbd7c1b8bf4cc273b774b14ec7.patch create mode 100644 patches/61150353bf9cc415f4554a9b4851c14e4255329f.patch create mode 100644 patches/6276c135d185e8492e8a2b9db5ca04e51c3293fa.patch create mode 100644 patches/62e86b42b5ed342d30c539e22810c26d312995e2.patch create mode 100644 patches/65bdf79da3f72269e6fe7aac1355df1420613889.patch create mode 100644 patches/68f2934a154abac9a2af72c55e4c08277172e087.patch create mode 100644 patches/6f4681bacc78a00a63766f12a17560701ab5c1e8.patch create mode 100644 patches/73c3a496cc8ce261e87abbd998b36ab16dab4f4b.patch create mode 100644 patches/75b27ef59cd0eb95b50d0cde14b05e0079b3ebe9.patch create mode 100644 patches/77f333b304424ae63dc70e10c6676dd645230f94.patch create mode 100644 patches/78e094632ec6160c3d2cfaad777c16a27ce08609.patch create mode 100644 patches/7a5d3abfb1aa3a38e0b3b3508c760fc8e712226c.patch create mode 100644 patches/7c84ba112429eb9bc0b99a6fe32a453c920a764c.patch create mode 100644 patches/7d6af6751c5726d884440d4e8d462a9ee6c5efc1.patch create mode 100644 patches/83980aca2086e5c4dca5aae9a92a065a9ff4ac56.patch create mode 100644 patches/8a18fb0f7396ceb1ca18cd82ca3deb795f5e60b2.patch create mode 100644 patches/8cef65fde3f92a84218fc338de6ab967fafd1820.patch create mode 100644 patches/8d470b57968fd875c2d9ce50446868b906f54752.patch create mode 100644 patches/8d48e3bbb2da2f5eb5f4a95efd6846e9ea93a160.patch create mode 100644 patches/92bc35f7b6cb4232be5ac4cc031202c7ad82260b.patch create mode 100644 patches/9abd746a327320048ae2b212f34edcadbcafcadf.patch create mode 100644 patches/9bb2a50e04460fff646830502d575b82dbf17055.patch create mode 100644 patches/9fe551ae49289ce6f693ca0dabf4c9c15164f67d.patch create mode 100644 patches/9ff52752d855722c55dbc71d9b22bd42eabfc468.patch create mode 100644 patches/a42e62fa0a59d0ba620889f97513929a113a6fbd.patch create mode 100644 patches/a7749fe451c37ec192b282ec7303b9809b49df93.patch create mode 100644 patches/a8c5f90b06c9bf2bfa2c2f4aedd7c395cb92195d.patch create mode 100644 patches/ab8995bbca73be761402585ead491111163c44d6.patch create mode 100644 patches/b03d3dc478ba13f405cf9a877a4894de096a1cc1.patch create mode 100644 patches/b3e0d272af149c4126f90a0262d796d7401ba7a1.patch create mode 100644 patches/b405aa2d0301c5fc448299501278ae2db4e15e50.patch create mode 100644 patches/b777552167d2651ceb13437f9fde4dca95045912.patch create mode 100644 patches/b94e59cc41f8eeb36ee269cae3275d7620189c14.patch create mode 100644 patches/bc5669eef8c1d747e82694547fd57a1400a5afec.patch create mode 100644 patches/bdaa76cfde64d06bb93c1f9102a0312d84cd0983.patch create mode 100644 patches/c26a8bbd6d0e7bbfa2891934a1af2934cab3b6bb.patch create mode 100644 patches/c5d18600ef3c5e795c4133cfd91a1df088f2252e.patch create mode 100644 patches/c9290dceee2cb6b882b26ec6e294560e51ef0853.patch create mode 100644 patches/c9e5e6a53aef5cd1b939ecfa18f56bdf5bf0451c.patch create mode 100644 patches/ce48709405270cae2dfdf99d9a8d57a4f672ad34.patch create mode 100644 patches/cf04ae54e680c0b28e8311459cb8fd11315485a0.patch create mode 100644 patches/d8cc2c1e4f8fa6bd49fe9c395353f9e24c7b51fc.patch create mode 100644 patches/d9cd4a33f53689bc0847775669a14f666a138fd7.patch create mode 100644 patches/dad56c39474377c7d47e261b380d0be3aed104cc.patch create mode 100644 patches/dad8e11e9fcbd76c0a2dc47211dcd654effed010.patch create mode 100644 patches/db4a97c4cbcb160b3754c803284dd0110d1de1e4.patch create mode 100644 patches/dd8f07223346b06da723c25a3ac42f874e6c945c.patch create mode 100644 patches/de597fca40d129435c53a69c6662d7bfac29771d.patch create mode 100644 patches/df7d9f383848dcb31a2f94bb1df5270ea21aff4b.patch create mode 100644 patches/e697ffbbcb41559c8de3ca3b94f3b9467e662a19.patch create mode 100644 patches/ea43e5e21d8aa61e00124f634a71325e6d3bfaa8.patch create mode 100644 patches/ec2826cc2e0b3a800836bcf8733dee0924f6b7ab.patch create mode 100644 patches/ecef6c7c809eba2a4eed5e281f19ab7331998c6f.patch create mode 100644 patches/edb5214b29cd7de06dd10f673986d38e568b077c.patch create mode 100644 patches/eefec8abda7cb8e8693aa876fbd1e21f2a6a5c2d.patch create mode 100644 patches/f7256d28d1c2f8340ab5b99df4bdb15aa232f3f3.patch create mode 100644 patches/fb1aa5624dff1d96249080fe365ed794431f45db.patch create mode 100644 patches/fff822fead6249671cbcb090b24bce58fab38de0.patch diff --git a/Cargo.toml b/Cargo.toml index 637d8af..6fb251f 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "core_io" -version = "0.1.20190701" +version = "0.1.20210325" authors = ["The Rust Project Developers", "Jethro Beekman"] license = "MIT/Apache-2.0" description = """ diff --git a/build-src.sh b/build-src.sh index f360202..a59e279 100755 --- a/build-src.sh +++ b/build-src.sh @@ -68,12 +68,4 @@ for IO_COMMIT in $OLD_COMMITS $(git_commits_ordered %H $NEW_COMMITS|tac); do fi done -if [ $(uname) == 'Darwin' ]; then - OLD_GIT_PERM=$(stat -f %Op .git) -else - OLD_GIT_PERM=$(stat --printf=%a .git) -fi -trap "chmod $OLD_GIT_PERM .git; exit 1" SIGINT -chmod 000 .git -cargo ${1:-package} -chmod $OLD_GIT_PERM .git +cargo ${1:-package} --allow-dirty diff --git a/build.rs b/build.rs index 26c0c44..0f47de2 100644 --- a/build.rs +++ b/build.rs @@ -12,7 +12,7 @@ fn parse_mappings(mut mappings: &'static str) -> Vec { // is why it's kind of weird. It should be changed to a saner format. const P1: &'static str = r#"-Mapping(""#; - const P2: &'static str = r#"",""#; ; + const P2: &'static str = r#"",""#; const P3: &'static str = "\")\n"; trait TakePrefix: Sized { diff --git a/edit-patches.sh b/edit-patches.sh index 90d4118..9aa1cb1 100755 --- a/edit-patches.sh +++ b/edit-patches.sh @@ -25,6 +25,7 @@ prompt_changes() { bold_arrow; echo "Replacing $IO_COMMIT.patch with updated version" git diff > $TMP_PATCH git clean -f -x + git reset -q HEAD~ git diff > $PATCH_DIR/$IO_COMMIT.patch rm -rf .git } diff --git a/functions.sh b/functions.sh index 85d3886..3a11b97 100644 --- a/functions.sh +++ b/functions.sh @@ -26,7 +26,7 @@ echo_lines() { get_io_commits() { for COMPILER_COMMIT in $COMPILER_COMMITS; do - IO_COMMIT=$(git log -n1 --pretty=format:%H $COMPILER_COMMIT -- src/libstd/io) + IO_COMMIT=$(git log -n1 --pretty=format:%H $COMPILER_COMMIT -- src/libstd/io library/std/src/io) if ! grep -q $COMPILER_COMMIT mapping.rs; then echo "-Mapping(\"$COMPILER_COMMIT\",\"$IO_COMMIT\")" >> mapping.rs fi @@ -40,8 +40,14 @@ get_patch_commits() { prepare_version() { mkdir src/$IO_COMMIT - git_extract src/libstd/io/ - if git_file_exists src/libcore/slice/memchr.rs; then + if git_file_exists library/std/src/io/mod.rs; then + git_extract library/std/src/io/ + else + git_extract src/libstd/io/ + fi + if git_file_exists library/core/src/slice/memchr.rs; then + true + elif git_file_exists src/libcore/slice/memchr.rs; then true elif git_file_exists src/libstd/sys_common/memchr.rs; then git_extract src/libstd/sys_common/memchr.rs @@ -84,6 +90,6 @@ bash_diff_loop() { ;; esac done - bash <> /dev/stderr + bash --rcfile <(custom_bashrc) <> /dev/stderr done } diff --git a/mapping.rs b/mapping.rs index a542729..a093448 100644 --- a/mapping.rs +++ b/mapping.rs @@ -1000,3 +1000,631 @@ -Mapping("00859e3e653973120006aaf3227823062dde1ba7","ead8d81301c1854e7ec251a57239813f6dfa8001") -Mapping("d628c2e642c6f8f85f24dd5d7f49de89b95bf682","ead8d81301c1854e7ec251a57239813f6dfa8001") -Mapping("d595b113584f8f446957469951fd5d31adc2a44e","bd17b5c9a2215cf8be8b2a361976730320a5f00f") +-Mapping("b9de4ef89e0e53099a084001b26ec3207c5f8391","1b946106b7955d3dcde26719b9b62a5a2c4b78fe") +-Mapping("a1dfd2490a6cb456b92e469fa550dc217e20ad6d","de597fca40d129435c53a69c6662d7bfac29771d") +-Mapping("7afe6d9d1f48b998cc88fe6f01ba0082788ba4b9","4436c9d35498e7ae3da261f6141d6d73b915e1e8") +-Mapping("56daaf669ebc3d5083db5cded719f780dc31104e","ec2826cc2e0b3a800836bcf8733dee0924f6b7ab") +-Mapping("e6ec0d125eba4074122b187032474b4174fb9d31","df7d9f383848dcb31a2f94bb1df5270ea21aff4b") +-Mapping("3ff10e74a74ed093fcabac1de27fe1cd65bbbb4a","bdaa76cfde64d06bb93c1f9102a0312d84cd0983") +-Mapping("c553e8e8812c19809e70523064989e66c5cfd3f1","e697ffbbcb41559c8de3ca3b94f3b9467e662a19") +-Mapping("4ad62488258972bdb0e2df225d100f99ef58dbad","7c84ba112429eb9bc0b99a6fe32a453c920a764c") +-Mapping("0a58f5864659ddfe1d95c122abaa75c88220aed0","4646a88b7a1e68326d092b9cbbbbdd616a51077f") +-Mapping("f2bbdd0a3257cc980c934a92c5bf9808cf31728c","56d288fa46e04cd5faf53d369a1a640a97e2bb08") +-Mapping("04caa632dd10c2bf64b69524c7f9c4c30a436877","8a18fb0f7396ceb1ca18cd82ca3deb795f5e60b2") +-Mapping("87cbf0a547aaf9e8a7fc708851ecf4bc2adab5fd","e697ffbbcb41559c8de3ca3b94f3b9467e662a19") +-Mapping("fa51f810e5b9254904b92660e7280b7d6a46f112","fb1aa5624dff1d96249080fe365ed794431f45db") +-Mapping("2225ee1b62ff089917434aefd9b2bf509cfa087f","8cef65fde3f92a84218fc338de6ab967fafd1820") +-Mapping("2e7244807a7878f6eca3eb7d97ae9b413aa49014","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("3525087ada7018ef227b10846648660b7f07b6d1","de597fca40d129435c53a69c6662d7bfac29771d") +-Mapping("45b3c28518e4c45dfd12bc2c4400c0d0e9639927","bc5669eef8c1d747e82694547fd57a1400a5afec") +-Mapping("a9c1c04e986dbf610be8cbe6a8107f90b4db61ce","75b27ef59cd0eb95b50d0cde14b05e0079b3ebe9") +-Mapping("0de96d37fbcc54978458c18f5067cd9817669bc8","2fee28e7138d8753487ed8895ce0f5f2e643ffad") +-Mapping("01a46509a4c2dc430ebebf940a26232fdaeeba81","2fee28e7138d8753487ed8895ce0f5f2e643ffad") +-Mapping("eb48d6bdee6c655d71f26594d47d232adf3e4e93","b03d3dc478ba13f405cf9a877a4894de096a1cc1") +-Mapping("6bb3dbfc6c6d8992d08431f320ba296a0c2f7498","fff822fead6249671cbcb090b24bce58fab38de0") +-Mapping("f455e46eae1a227d735091091144601b467e1565","fff822fead6249671cbcb090b24bce58fab38de0") +-Mapping("31dd4f4acbcbdb02b0745d2136399ed664a28050","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("50fc24d8a172a853b5dfe40702d6550e3b8562ba","6276c135d185e8492e8a2b9db5ca04e51c3293fa") +-Mapping("a1912f2e89b77cfe2a0e64b96f444848fe4e2d49","df7d9f383848dcb31a2f94bb1df5270ea21aff4b") +-Mapping("db0492ace429cfeb3567e2c04e300be7df9972ff","2c31b45ae878b821975c4ebd94cc1e49f6073fd0") +-Mapping("17e73e801a75559eac5c932ff07bd9c8499a1364","edb5214b29cd7de06dd10f673986d38e568b077c") +-Mapping("75e1463c52aaea25bd32ed53c73797357e561cce","05fc7faacb7c33eaad6614f62a7d560b0d2660a5") +-Mapping("2d8a3b9181f41d3af9b9f016c5d73b2553e344bf","6f4681bacc78a00a63766f12a17560701ab5c1e8") +-Mapping("ed8b708c1a6bf6d94f860eeb6a6b0b442c380d7f","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("5fa22fe6f821ac3801d05f624b123dda25fde32c","410550665601a8abe8935f7b55d5732fe4c4224f") +-Mapping("a9cd294cf2775441e713c7ee2918b728733b99f5","5acb7f198fa56943a2837583d555896badb5733d") +-Mapping("0ca7f74dbd23a3e8ec491cd3438f490a3ac22741","5304511fbc1f9a0c7340f7f0d037aa4dd13a588f") +-Mapping("e599b53e67ddd197a09a3d8720eed872df481aa0","65bdf79da3f72269e6fe7aac1355df1420613889") +-Mapping("a2f8f6281817d430e20726128b739d3c6708561c","9abd746a327320048ae2b212f34edcadbcafcadf") +-Mapping("7750c3d46bc19784adb1ee6e37a5ec7e4cd7e772","6276c135d185e8492e8a2b9db5ca04e51c3293fa") +-Mapping("c43d03a19f326f4a323569328cc501e86eb6d22e","dad56c39474377c7d47e261b380d0be3aed104cc") +-Mapping("95b1fe560d2bd8472f250fb8cfd2168520a58405","04f0d309dcbaa8425c702d1439592b87fff0a69e") +-Mapping("8aa18cbdc5d4bc33bd61e2d9a4b643d87f5d21de","5304511fbc1f9a0c7340f7f0d037aa4dd13a588f") +-Mapping("9b4154193e8471f36b1a9e781f1ef7d492fc6a6c","9fe551ae49289ce6f693ca0dabf4c9c15164f67d") +-Mapping("9778068cbc1e06cc3685422323ff38a2f397de26","410550665601a8abe8935f7b55d5732fe4c4224f") +-Mapping("bad3bf622bded50a97c0a54e29350eada2a3a169","05fc7faacb7c33eaad6614f62a7d560b0d2660a5") +-Mapping("26438b473883ea607b30288e461187f0fb2fe589","0506789014f9aef9ffac7d7d1e22fa72c7b85ab7") +-Mapping("52fa23add6fb0776b32cc591ac928618391bdf41","5768385615c61f6c9d63dccfb3548812f1ba1320") +-Mapping("890881f8f4c77e8670d4b32104c0325fcfefc90f","b94e59cc41f8eeb36ee269cae3275d7620189c14") +-Mapping("2f517ce6f28b5d638cce4c1eccdbe63255b11420","5304511fbc1f9a0c7340f7f0d037aa4dd13a588f") +-Mapping("c23a7aa778b0dfeffbf83b099bdf971242c1e1ac","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("d8bdb3fdcbd88eb16e1a6669236122c41ed2aed3","4436c9d35498e7ae3da261f6141d6d73b915e1e8") +-Mapping("285fc7d704fcdd7b2a37d475d04d5d955490e000","9fe551ae49289ce6f693ca0dabf4c9c15164f67d") +-Mapping("fe10f1a49f5ca46e57261b95f46f519523f418fe","d8cc2c1e4f8fa6bd49fe9c395353f9e24c7b51fc") +-Mapping("9ed29b6ff6aa2e048b09c27af8f62ee3040bdb37","9bb2a50e04460fff646830502d575b82dbf17055") +-Mapping("ae1b871cca56613b1af1a5121dd24ac810ff4b89","92bc35f7b6cb4232be5ac4cc031202c7ad82260b") +-Mapping("7ebd87a7a1e0e21767422e115c9455ef6e6d4bee","fb1aa5624dff1d96249080fe365ed794431f45db") +-Mapping("593fe977a77ad5a7aec23c6cb0f86a3470221670","bdaa76cfde64d06bb93c1f9102a0312d84cd0983") +-Mapping("a85e94927622665a9e9022de0d33a890a2e32d43","5acb7f198fa56943a2837583d555896badb5733d") +-Mapping("e620d0f337d0643c757bab791fc7d88d63217704","df7d9f383848dcb31a2f94bb1df5270ea21aff4b") +-Mapping("2111aed0a38c819acb140c7153e9366964a37f2f","dad56c39474377c7d47e261b380d0be3aed104cc") +-Mapping("4295eea903a9e1014ee30f82930f5ec08d888077","edb5214b29cd7de06dd10f673986d38e568b077c") +-Mapping("20fc02f836f3035b86b56a7cedb97c5cd4ed9612","5768385615c61f6c9d63dccfb3548812f1ba1320") +-Mapping("caa231d998a5e853c7ba1455d7a05b500df9d63c","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("6fd8798f4de63328d743eb2a9a9c12e202a4a182","b3e0d272af149c4126f90a0262d796d7401ba7a1") +-Mapping("0148b971c921a0831fbf3357e5936eec724e3566","250eeb4c3c00b7831226cf5266aacb5fca1e13f3") +-Mapping("45ebd5808afd3df7ba842797c0fcd4447ddf30fb","5d90154886039ddbd7c1b8bf4cc273b774b14ec7") +-Mapping("05762e3d6f5facafdd47efdf4203021fadf61bb1","2c31b45ae878b821975c4ebd94cc1e49f6073fd0") +-Mapping("99111606fcda4fdb0646e4f7ee0f6cbcb76fb84a","9fe551ae49289ce6f693ca0dabf4c9c15164f67d") +-Mapping("349b3b324dade7ca638091db93ba08bbc443c63d","bdaa76cfde64d06bb93c1f9102a0312d84cd0983") +-Mapping("74e80468347471779be6060d8d7d6d04e98e467f","05fc7faacb7c33eaad6614f62a7d560b0d2660a5") +-Mapping("c798dffac9dc8c82374db48f5b474690cc6e9686","b94e59cc41f8eeb36ee269cae3275d7620189c14") +-Mapping("61f5a0092364061ec5649ca98d5e3e9b927880fe","0506789014f9aef9ffac7d7d1e22fa72c7b85ab7") +-Mapping("f3c9cece7b6829e6fd7854a1aee6a1619a81a38c","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("a37c32e2d5fb186627ffe99a391c7fd6fd159334","ec2826cc2e0b3a800836bcf8733dee0924f6b7ab") +-Mapping("85976442558bf2d09cec3aa49c9c9ba86fb15c1f","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("d79f1bd31a1401b5d08096fcdf9a9eb23ddf95df","05fc7faacb7c33eaad6614f62a7d560b0d2660a5") +-Mapping("81e754c359c471f91263813c46c67955071716a7","2c31b45ae878b821975c4ebd94cc1e49f6073fd0") +-Mapping("cdc8f0606d0f3c4f3866643382c8a5776d1bdaed","0af3bd01dfae488392dc6f08daa2d0d8d370fb00") +-Mapping("14061868b3960d8a68a079bd276dde85936970ac","5768385615c61f6c9d63dccfb3548812f1ba1320") +-Mapping("dbf8b6bf116c7bece2987ff4bd2792f008a6ee77","5768385615c61f6c9d63dccfb3548812f1ba1320") +-Mapping("14b15521c52549ebbb113173b4abecd124b5a823","5768385615c61f6c9d63dccfb3548812f1ba1320") +-Mapping("2987785df3d46d5ff144a5c67fbb8f5cca798d78","8cef65fde3f92a84218fc338de6ab967fafd1820") +-Mapping("58b834344fc7b9185e7a50db1ff24e5eb07dae5e","c9290dceee2cb6b882b26ec6e294560e51ef0853") +-Mapping("b122908617436af187252572ed5db96850551380","8a18fb0f7396ceb1ca18cd82ca3deb795f5e60b2") +-Mapping("13db6501c7273cd1997ce20e15106f362e5613c4","9bb2a50e04460fff646830502d575b82dbf17055") +-Mapping("35dbef235048f9a2939dc20effe083ca483c37ff","bc5669eef8c1d747e82694547fd57a1400a5afec") +-Mapping("346aec9b02f3c74f3fce97fd6bda24709d220e49","5304511fbc1f9a0c7340f7f0d037aa4dd13a588f") +-Mapping("bbb664a99c0188fa756cbbb3a6c4e5d8825c372b","413ab57c0210ecbe92298c53ec4e1e39f97e4e4c") +-Mapping("1721c9685b1ee69f1e17b3a8b09145b10fdfbe4a","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("98d66340d6e63eda115afc8b0da1d87965881936","30e49a9ead550551e879af64ba91a0316da1c422") +-Mapping("15812785344d913d779d9738fe3cca8de56f71d5","61150353bf9cc415f4554a9b4851c14e4255329f") +-Mapping("74c4e6a981d3150db8444c8d250e50bbe6b93b6b","4646a88b7a1e68326d092b9cbbbbdd616a51077f") +-Mapping("6af1bdda54abc9e919fc1137411dfc4311e05649","9fe551ae49289ce6f693ca0dabf4c9c15164f67d") +-Mapping("46e85b4328fe18492894093c1092dfe509df4370","05fc7faacb7c33eaad6614f62a7d560b0d2660a5") +-Mapping("576d27c5a6c80cd39ef57d7398831d8e177573cc","2c31b45ae878b821975c4ebd94cc1e49f6073fd0") +-Mapping("fe1bf8e05c39bdcc73fc09e246b7209444e389bc","c26a8bbd6d0e7bbfa2891934a1af2934cab3b6bb") +-Mapping("5c5c8eb864e56ce905742b8e97df5506bba6aeef","92bc35f7b6cb4232be5ac4cc031202c7ad82260b") +-Mapping("043f6d747c15068f0053a0542e9b0f17ae7f4de4","65bdf79da3f72269e6fe7aac1355df1420613889") +-Mapping("bc1571cc3cfef07251f7df52b95525aa16797ca2","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("618768492f0c731fcb770dc2d178abe840846419","b03d3dc478ba13f405cf9a877a4894de096a1cc1") +-Mapping("fba38ac27e2ade309f4c2504a6d6cd3556972a28","edb5214b29cd7de06dd10f673986d38e568b077c") +-Mapping("6470169237833d02c399568a375d9b47cbfaeccc","5d8fe1c4e6b214916de690ee25c17f862e166a28") +-Mapping("699f83f525c985000c1f70bf85117ba383adde87","03c64bf532ceec915f74460daf5344bb8ccf23d3") +-Mapping("16957bd4d3a5377263f76ed74c572aad8e4b7e59","5304511fbc1f9a0c7340f7f0d037aa4dd13a588f") +-Mapping("fc5deca2143a448d10a1241a777275e59448c94d","2fee28e7138d8753487ed8895ce0f5f2e643ffad") +-Mapping("bb178237c5539c75e1b85ab78a8ab902b1f333d5","8cef65fde3f92a84218fc338de6ab967fafd1820") +-Mapping("31530e5d132ebcc3654baf2e5460599681520af0","5acb7f198fa56943a2837583d555896badb5733d") +-Mapping("d1e81ef234ff5c2e0e3a69cb4e8e5f5b0fe1fd83","39c52225dd06ab06ef75ef97841c66c7d9b6e56c") +-Mapping("0b644e419681835bd0f5871c3bfbd648aa04f157","8cef65fde3f92a84218fc338de6ab967fafd1820") +-Mapping("4f7612ac1499258025077f1fd05d2f429f9accfb","56d288fa46e04cd5faf53d369a1a640a97e2bb08") +-Mapping("6e310f2abae97323ca1d5469657b83aa1a9407e0","c5d18600ef3c5e795c4133cfd91a1df088f2252e") +-Mapping("1d0d76f8dd4f5f6ecbeab575b87edaf1c9f56bb8","9abd746a327320048ae2b212f34edcadbcafcadf") +-Mapping("673d0db5e393e9c64897005b470bfeb6d5aec61b","db4a97c4cbcb160b3754c803284dd0110d1de1e4") +-Mapping("488381ce9ef0ceabe83b73127c659e5d38137df0","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("130359cb05246fcacdde61baa2613419ef6570c7","d9cd4a33f53689bc0847775669a14f666a138fd7") +-Mapping("18c275b423f9f13c0e404ae3804967d2ab66337c","7c84ba112429eb9bc0b99a6fe32a453c920a764c") +-Mapping("a08c47310c7d49cbdc5d7afb38408ba519967ecd","fb1aa5624dff1d96249080fe365ed794431f45db") +-Mapping("30f0a07684f6c1f5df62d69e9519d82e13d6bf2d","a7749fe451c37ec192b282ec7303b9809b49df93") +-Mapping("7870050796e5904a0fc85ecbe6fa6dde1cfe0c91","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("215f2d3294b08dbdcf8f7d40de21ef1e7eae0a2d","05fc7faacb7c33eaad6614f62a7d560b0d2660a5") +-Mapping("72da5a9d85a522b11e80d0fdd1fd95247d442604","bdaa76cfde64d06bb93c1f9102a0312d84cd0983") +-Mapping("acca818928654807ed3bc1ce0e97df118f8716c8","ab8995bbca73be761402585ead491111163c44d6") +-Mapping("c2d141df59703393c0c683abc259f9a8c3be041a","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("0aa6751c19d3ba80df5b0b02c00bf44e13c97e80","05fc7faacb7c33eaad6614f62a7d560b0d2660a5") +-Mapping("25f6938da459a57b43bdf16ed6bdad3225b2a3ce","77f333b304424ae63dc70e10c6676dd645230f94") +-Mapping("397b390cc76ba1d98f80b2a24a371f708dcc9169","6f4681bacc78a00a63766f12a17560701ab5c1e8") +-Mapping("d6e4028a0db6b13d9a603baad109d6c902802c03","e697ffbbcb41559c8de3ca3b94f3b9467e662a19") +-Mapping("2890b37b861247de3b8c6ba2ecbcd00048c728a1","7c84ba112429eb9bc0b99a6fe32a453c920a764c") +-Mapping("2753fab7ce3647033146b07c8b6c9f4856a910b0","5304511fbc1f9a0c7340f7f0d037aa4dd13a588f") +-Mapping("7cdbc87a49b0b705a41a004a6d486b0952521ae7","5d90154886039ddbd7c1b8bf4cc273b774b14ec7") +-Mapping("4fb54ed484e2239a3e9eff3be17df00d2a162be3","fff822fead6249671cbcb090b24bce58fab38de0") +-Mapping("9912925c254589f58338cb2993163e618475ff75","05fc7faacb7c33eaad6614f62a7d560b0d2660a5") +-Mapping("6e0d27d9368e2982bef8e1c4ac14d622c5ad018e","9ff52752d855722c55dbc71d9b22bd42eabfc468") +-Mapping("3291ae33907f2a866ea6cea89113200555038d06","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("5180f3da5fd72627a8d38558ad1297df38793acd","78e094632ec6160c3d2cfaad777c16a27ce08609") +-Mapping("43a5ff4222e1f217ac14331afd59f82ec4204d12","b03d3dc478ba13f405cf9a877a4894de096a1cc1") +-Mapping("bdfd698f37184da42254a03ed466ab1f90e6fb6c","dad56c39474377c7d47e261b380d0be3aed104cc") +-Mapping("6d69caba110c0c2fb90180df1cbc8be5033b91d4","b3e0d272af149c4126f90a0262d796d7401ba7a1") +-Mapping("4a20eb6a9da36c88ee929826c4f1eb8d7ea393b2","7d6af6751c5726d884440d4e8d462a9ee6c5efc1") +-Mapping("8417d68de5e063426ab6bb7f383df6117d1beeed","9bb2a50e04460fff646830502d575b82dbf17055") +-Mapping("0c03aee8b81185d65b5821518661c30ecdb42de5","5304511fbc1f9a0c7340f7f0d037aa4dd13a588f") +-Mapping("8431f261dd160021b6af85916f161a13dd101ca0","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("084beb83e0e87d673d5fabc844d28e8e8ae2ab4c","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("1f5bc176b0e54a8e464704adcd7e571700207fe9","8cef65fde3f92a84218fc338de6ab967fafd1820") +-Mapping("760226733e940cb375f791e894fbb554555eeb01","edb5214b29cd7de06dd10f673986d38e568b077c") +-Mapping("76b11980ad416c3ad6143504c2277757ecacf9b5","08f2904dfaf5e75fbcc1305c8b0aad5fae71a4ff") +-Mapping("a6946a817a1345ce739acd8b12255c0a595e9b39","b03d3dc478ba13f405cf9a877a4894de096a1cc1") +-Mapping("d3f8a0b5dfddfe443d9db1f1da18348dbceb0e47","9ff52752d855722c55dbc71d9b22bd42eabfc468") +-Mapping("ca3766e2e58f462a20922e42c821a37eaf0e13db","a8c5f90b06c9bf2bfa2c2f4aedd7c395cb92195d") +-Mapping("ffa2e7ae8fbf9badc035740db949b9dae271c29f","5acb7f198fa56943a2837583d555896badb5733d") +-Mapping("fa0f7d0080d8e7e9eb20aa9cbf8013f96c81287f","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("f844ea1e561475e6023282ef167e76bc973773ef","5304511fbc1f9a0c7340f7f0d037aa4dd13a588f") +-Mapping("76a252ea9e7be93a61ffdf33b3533e24a9cf459d","92bc35f7b6cb4232be5ac4cc031202c7ad82260b") +-Mapping("f74583445702e2e27ec4415376f2c540a83d7ded","8cef65fde3f92a84218fc338de6ab967fafd1820") +-Mapping("4d0dd02ee07bddad9136f95c9f7846ebf3eb3fc5","9abd746a327320048ae2b212f34edcadbcafcadf") +-Mapping("1572c433eed495d0ade41511ae106b180e02851d","5d90154886039ddbd7c1b8bf4cc273b774b14ec7") +-Mapping("dd7fc54ebdca419ad9d3ab1e9f5ed14e770768ea","de597fca40d129435c53a69c6662d7bfac29771d") +-Mapping("32c654a9795b0d88541e56ba9da4150e34f1d5f9","dad8e11e9fcbd76c0a2dc47211dcd654effed010") +-Mapping("a8cf3991177f30694200002cd9479ffbbe6d9a1a","fff822fead6249671cbcb090b24bce58fab38de0") +-Mapping("f781babf87dea29c44f93842b7ac9eb809549d29","5304511fbc1f9a0c7340f7f0d037aa4dd13a588f") +-Mapping("0262de554b4c4c5af346137bbb1664a3f6cf4df2","ec2826cc2e0b3a800836bcf8733dee0924f6b7ab") +-Mapping("3ed3b8bb7b100afecf7d5f52eafbb70fec27f537","92bc35f7b6cb4232be5ac4cc031202c7ad82260b") +-Mapping("ddf43867a9cbb3766b48552632a602498fae2699","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("234781afe33d3f339b002f85f948046d8476cfc9","68f2934a154abac9a2af72c55e4c08277172e087") +-Mapping("0e8a4b441c5da21a2cb19448728ade5baa299c66","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("c609b2eaf323186a1167ec1a9ffa69a7d4a5b1b9","8cef65fde3f92a84218fc338de6ab967fafd1820") +-Mapping("564758c4c329e89722454dd2fbb35f1ac0b8b47c","83980aca2086e5c4dca5aae9a92a065a9ff4ac56") +-Mapping("3a3f4a7cbaff09722b8c7cc8f09ce86ff5f953a3","4646a88b7a1e68326d092b9cbbbbdd616a51077f") +-Mapping("91fd6283e658e2c7aab2d3f5206fc1891f486af2","e697ffbbcb41559c8de3ca3b94f3b9467e662a19") +-Mapping("5e65467eff3d1da4712586d8402d1d2e1d6654bc","a42e62fa0a59d0ba620889f97513929a113a6fbd") +-Mapping("b7ebc6b0c1ba3c27ebb17c0b496ece778ef11e18","bdaa76cfde64d06bb93c1f9102a0312d84cd0983") +-Mapping("f0b58fcf03391a91f74224fe38a696d5a5b789d9","b03d3dc478ba13f405cf9a877a4894de096a1cc1") +-Mapping("3dbade652ed8ebac70f903e01f51cd92c4e4302c","83980aca2086e5c4dca5aae9a92a065a9ff4ac56") +-Mapping("d8cbd9caca648ecdb66ff4c945c060762aa6297f","2c31b45ae878b821975c4ebd94cc1e49f6073fd0") +-Mapping("7dbfb0a8ca4ab74ee3111e57a024f9e6257ce37c","92bc35f7b6cb4232be5ac4cc031202c7ad82260b") +-Mapping("e2267046859c9ceb932abc983561d53a117089f6","8cef65fde3f92a84218fc338de6ab967fafd1820") +-Mapping("27d6f55f47e8875e71083a28ed84ea5a88e1b596","92bc35f7b6cb4232be5ac4cc031202c7ad82260b") +-Mapping("5be3f9f10e9fd59ea03816840a6051413fbdefae","bdaa76cfde64d06bb93c1f9102a0312d84cd0983") +-Mapping("3e0a1c09108b52e41113520c7fa516480a8b67f9","4646a88b7a1e68326d092b9cbbbbdd616a51077f") +-Mapping("158f8d034b15e65ba8dc0d066358dd0632bfcd6e","8cef65fde3f92a84218fc338de6ab967fafd1820") +-Mapping("c71248b70870960af9993de4f31d3cba9bbce7e8","de597fca40d129435c53a69c6662d7bfac29771d") +-Mapping("6ef275e6c3cb1384ec78128eceeb4963ff788dca","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("7bade6ef730cff83f3591479a98916920f66decd","5acb7f198fa56943a2837583d555896badb5733d") +-Mapping("73dc675b9437c2a51a975a9f58cc66f05463c351","0af3bd01dfae488392dc6f08daa2d0d8d370fb00") +-Mapping("d98d2f57d9b98325ff075c343d2c7695b66dfa7d","4e27ed3af19e604d7b65e130145fcecdc69fba7a") +-Mapping("0e63af5da3400ace48a0345117980473fd21ad73","1bf130519ca1c020623a550dc6b250eacea68e72") +-Mapping("4560cb830fce63fcffdc4558f4281aaac6a3a1ba","b405aa2d0301c5fc448299501278ae2db4e15e50") +-Mapping("11c94a197726b6a981828cb1837d7c3eed1b841d","8cef65fde3f92a84218fc338de6ab967fafd1820") +-Mapping("7a9b552cb1621c9c57898d147228aab32b65a7c3","0506789014f9aef9ffac7d7d1e22fa72c7b85ab7") +-Mapping("c27f7568bc74c418996892028a629eed5a7f5f00","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("d2230290f7220e740ec08f4d844bf5951e1b74b8","5768385615c61f6c9d63dccfb3548812f1ba1320") +-Mapping("f9d422ea78a4652c5d9ecd6b6d7577bdfbfd98a8","2c31b45ae878b821975c4ebd94cc1e49f6073fd0") +-Mapping("618b01f9fa0a6b4e7e2ce5b3409abe104b80c4a8","413ab57c0210ecbe92298c53ec4e1e39f97e4e4c") +-Mapping("8ad7bc3f428300aee6764f6e23527e19eb235e81","471dd52d7710dcad5fec0cd731b836b02ba4a8f4") +-Mapping("60960a260f7b5c695fd0717311d72ce62dd4eb43","dad56c39474377c7d47e261b380d0be3aed104cc") +-Mapping("433aae93e4ef866a1fdfefad136b32ed89acd3e7","df7d9f383848dcb31a2f94bb1df5270ea21aff4b") +-Mapping("a44774c3a9739b2eea8923e09d67b14312c78ef3","413ab57c0210ecbe92298c53ec4e1e39f97e4e4c") +-Mapping("f5d8117c338a788bd24abec733fd143dfceb25a0","ab8995bbca73be761402585ead491111163c44d6") +-Mapping("d3c79346a3e7ddbb5fb417810f226ac5a9209007","7c84ba112429eb9bc0b99a6fe32a453c920a764c") +-Mapping("3761dcd3467441f78939ccb3b341b03b6a7558d7","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("c5840f9d252c2f5cc16698dbf385a29c5de3ca07","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("8e21bd0633b8d970646ee6eb706c9e8acfad19af","a7749fe451c37ec192b282ec7303b9809b49df93") +-Mapping("53df91a9b24ad999e7ca896447af6f5f74fe43bc","edb5214b29cd7de06dd10f673986d38e568b077c") +-Mapping("dddb7fca09dc817ba275602b950bb81a9032fb6d","b405aa2d0301c5fc448299501278ae2db4e15e50") +-Mapping("fb1dc34a831688f8eca89ea22ea2eb39e881d729","9fe551ae49289ce6f693ca0dabf4c9c15164f67d") +-Mapping("4f03f4a989d1c8346c19dfb417a77c09b34408b8","5b5196ad65db877c2f140dfc7a25f3fc6f2e40c6") +-Mapping("38d911dfc55a7a1eea1c80139113ed2ff0151087","de597fca40d129435c53a69c6662d7bfac29771d") +-Mapping("3eeb8d4f2fbae0bb1c587d00b5abeaf938da47f4","92bc35f7b6cb4232be5ac4cc031202c7ad82260b") +-Mapping("212b2c7da87f3086af535b33a9ca6b5242f2d5a7","9bb2a50e04460fff646830502d575b82dbf17055") +-Mapping("663d2f5cd3163f17eddb74ee1e028d542255f21a","78e094632ec6160c3d2cfaad777c16a27ce08609") +-Mapping("436494b8f8008b600d64b3951f63c2bb0ea81673","df7d9f383848dcb31a2f94bb1df5270ea21aff4b") +-Mapping("65b448273dd280401cd440a6740a7cd891525ba3","fb1aa5624dff1d96249080fe365ed794431f45db") +-Mapping("521d78407471cb78e9bbf47160f6aa23047ac499","edb5214b29cd7de06dd10f673986d38e568b077c") +-Mapping("043eca7f0b34d12e61c44206beca740628647080","5acb7f198fa56943a2837583d555896badb5733d") +-Mapping("485c5fb6e1bf12cd11a8fac5ee94962e17cff74b","5768385615c61f6c9d63dccfb3548812f1ba1320") +-Mapping("d32c320d7eee56706486fef6be778495303afe9e","2c56ea38b045624dc8b42ec948fc169eaff1206a") +-Mapping("e5e33ebd2ba12a78dbf6e2d5f154d5f71f28576c","2c31b45ae878b821975c4ebd94cc1e49f6073fd0") +-Mapping("e37f25aa3f356546ab851e394d5598fc575eabda","bdaa76cfde64d06bb93c1f9102a0312d84cd0983") +-Mapping("71f9384e3bec467158a628e2d11e77ffada16a90","c5d18600ef3c5e795c4133cfd91a1df088f2252e") +-Mapping("cf9cf7c923eb01146971429044f216a3ca905e06","77f333b304424ae63dc70e10c6676dd645230f94") +-Mapping("ff5b446d2fdbd898bc97a751f2f72858de185cf1","6276c135d185e8492e8a2b9db5ca04e51c3293fa") +-Mapping("98edd1fbf8a68977a2a7c1312eb1ebff80515a92","de597fca40d129435c53a69c6662d7bfac29771d") +-Mapping("a605441e049f0b6d5f7715b94b8ac4662fd7fcf6","92bc35f7b6cb4232be5ac4cc031202c7ad82260b") +-Mapping("a5b09d35473615e7142f5570f5c5fad0caf68bd2","08f2904dfaf5e75fbcc1305c8b0aad5fae71a4ff") +-Mapping("fae75cd216c481de048e4951697c8f8525669c65","e697ffbbcb41559c8de3ca3b94f3b9467e662a19") +-Mapping("246be7e1a557b8ac8287c6842379a0db67770be6","e697ffbbcb41559c8de3ca3b94f3b9467e662a19") +-Mapping("2935d294ff862fdf96578d0cbbdc289e8e7ba81c","fff822fead6249671cbcb090b24bce58fab38de0") +-Mapping("f315c35a77e40bd11ce81fedc0556be0f410bbf4","fff822fead6249671cbcb090b24bce58fab38de0") +-Mapping("61edfd591cedff66fca639c02f66984f6271e5a6","db4a97c4cbcb160b3754c803284dd0110d1de1e4") +-Mapping("c6e9c76c59e3c10acd63ca9ec157a8894ea1a068","1b946106b7955d3dcde26719b9b62a5a2c4b78fe") +-Mapping("f43c34a134358471726f25fe5973b8c7e177c825","9bb2a50e04460fff646830502d575b82dbf17055") +-Mapping("98f8cce6db6c6c6660eeffee2b3903104e547ecf","c26a8bbd6d0e7bbfa2891934a1af2934cab3b6bb") +-Mapping("0c987c5c02498b4e77f5dfae1f6914ffb9268575","413ab57c0210ecbe92298c53ec4e1e39f97e4e4c") +-Mapping("e44fdf97929d1315add3b76208adf99e8299252d","edb5214b29cd7de06dd10f673986d38e568b077c") +-Mapping("2d1a551e144335e0d60a637d12f410cf65849876","dad56c39474377c7d47e261b380d0be3aed104cc") +-Mapping("fd4b177aabb9749dfb562c48e47379cea81dc277","ec2826cc2e0b3a800836bcf8733dee0924f6b7ab") +-Mapping("0e2c1281e909ca38479b97962fc9248f75d66412","9fe551ae49289ce6f693ca0dabf4c9c15164f67d") +-Mapping("d1e594f4029c6ac8feb7c2acf9f9e04c1b9c493c","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("338f939a8d77061896cd0a1ca87a2c6d1f4ec359","56d288fa46e04cd5faf53d369a1a640a97e2bb08") +-Mapping("44e3daf5eee8263dfc3a2509e78ddd1f6f783a0e","8cef65fde3f92a84218fc338de6ab967fafd1820") +-Mapping("91a79fb29ac78d057d04dbe86be13d5dcc64309a","de597fca40d129435c53a69c6662d7bfac29771d") +-Mapping("42abbd8878d3b67238f3611b0587c704ba94f39c","5768385615c61f6c9d63dccfb3548812f1ba1320") +-Mapping("bea0372a1a7a31b81f28cc4d9a83a2dc9a79d008","edb5214b29cd7de06dd10f673986d38e568b077c") +-Mapping("0beb2ba16a08dfa01569b5f4644da315dc4c806c","390f717a0af5851271792da9ff235c95f3db2556") +-Mapping("0fc6756b42e0556cc2e18079f5fc6b4d58f4e81a","410550665601a8abe8935f7b55d5732fe4c4224f") +-Mapping("5404efc28a0cddee103ef6396c48ea71ff9631c8","77f333b304424ae63dc70e10c6676dd645230f94") +-Mapping("3e525e3f6d9e85d54fa4c49b52df85aa0c990100","413ab57c0210ecbe92298c53ec4e1e39f97e4e4c") +-Mapping("394e1b40d264aa6928811919c1124fa248e7d802","6276c135d185e8492e8a2b9db5ca04e51c3293fa") +-Mapping("e413dc36a83a5aad3ab6270373000693a917e92b","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("ded5ee0013f6126f885baf5e072c20ba8b86ee6a","413ab57c0210ecbe92298c53ec4e1e39f97e4e4c") +-Mapping("99cb9ccb9ca2067ad6e60508e3d52da77396b2f1","05fc7faacb7c33eaad6614f62a7d560b0d2660a5") +-Mapping("f9a3086363f214f2b56bef30f0ac572e1a9127f1","471dd52d7710dcad5fec0cd731b836b02ba4a8f4") +-Mapping("02046a5d402c789c006d0da7662f800fe3c45faf","03c64bf532ceec915f74460daf5344bb8ccf23d3") +-Mapping("2454a68cfbb63aa7b8e09fe05114d5f98b2f9740","fb1aa5624dff1d96249080fe365ed794431f45db") +-Mapping("feb3536eba10c2e4585d066629598f03d5ddc7c6","ec2826cc2e0b3a800836bcf8733dee0924f6b7ab") +-Mapping("00ee1b47f42129a0a6e33510578fbcf07c1e5382","dad56c39474377c7d47e261b380d0be3aed104cc") +-Mapping("237d54ff6c4fb3577e02d4c5af02813c11b63d01","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("435236b8877cdb98c82eaebfb7887782277265c5","9ff52752d855722c55dbc71d9b22bd42eabfc468") +-Mapping("8e54a21139ae96a2aca3129100b057662e2799b9","410550665601a8abe8935f7b55d5732fe4c4224f") +-Mapping("154f1f544dd68f7b53ff8d9952811e855f4c2d7c","c9e5e6a53aef5cd1b939ecfa18f56bdf5bf0451c") +-Mapping("50f8aadd746ebc929a752e5ffb133936ee75c52f","e697ffbbcb41559c8de3ca3b94f3b9467e662a19") +-Mapping("ad7c55e1fc55d9af4787b285cec1c64e3480ae84","dad56c39474377c7d47e261b380d0be3aed104cc") +-Mapping("9b0edb7fddacd6a60a380c1ce59159de597ab270","7d6af6751c5726d884440d4e8d462a9ee6c5efc1") +-Mapping("e2be5f568d1f60365b825530f5b5cb722460591b","9fe551ae49289ce6f693ca0dabf4c9c15164f67d") +-Mapping("e87a205c2e117d9fb57f6cdeac0a7f6e95c88316","413ab57c0210ecbe92298c53ec4e1e39f97e4e4c") +-Mapping("032a53a06ce293571e51bbe621a5c480e8a28e95","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("c0e02ad724f05f73b957b3d6f6314a9a2e5c284e","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("5fa0af2327944bd806b2fa382d4e983149ae7e4a","413ab57c0210ecbe92298c53ec4e1e39f97e4e4c") +-Mapping("0da58007451a154da2480160429e1604a1f5f0ec","65bdf79da3f72269e6fe7aac1355df1420613889") +-Mapping("7f7a1cbfd3b55daee191247770627afab09eece2","c9e5e6a53aef5cd1b939ecfa18f56bdf5bf0451c") +-Mapping("34e82a7b793a6cdd27df762bf46bab8cdc92b14a","b03d3dc478ba13f405cf9a877a4894de096a1cc1") +-Mapping("d006f5734f49625c34d6fc33bf6b9967243abca8","6f4681bacc78a00a63766f12a17560701ab5c1e8") +-Mapping("7efc097c4fe6e97f54a44cee91c56189e9ddb41c","8cef65fde3f92a84218fc338de6ab967fafd1820") +-Mapping("2fbb07525e2f07a815e780a4268b11916248b5a9","03c64bf532ceec915f74460daf5344bb8ccf23d3") +-Mapping("94736c434ee154b30e2ec22ec112b79e3f6c5884","eefec8abda7cb8e8693aa876fbd1e21f2a6a5c2d") +-Mapping("fd542592f08ca0d1f7255600115c2eafdf6b5da7","5acb7f198fa56943a2837583d555896badb5733d") +-Mapping("7f3df5772439eee1c512ed2eb540beef1124d236","5768385615c61f6c9d63dccfb3548812f1ba1320") +-Mapping("1edd389cc4c7b5be7a3dd4fe4b986f6017018e54","39c52225dd06ab06ef75ef97841c66c7d9b6e56c") +-Mapping("ad4bc3323b9299d867697e9653dcea1b5e1ad283","05fc7faacb7c33eaad6614f62a7d560b0d2660a5") +-Mapping("a143517d44cac50b20cbd3a0b579addab40dd399","410550665601a8abe8935f7b55d5732fe4c4224f") +-Mapping("a29424a2265411dda7d7446516ac5fd7499e2b55","df7d9f383848dcb31a2f94bb1df5270ea21aff4b") +-Mapping("7f65393b9abf5e70d0b9a8080558f17c5625bd40","fb1aa5624dff1d96249080fe365ed794431f45db") +-Mapping("d1206f950ffb76c76e1b74a19ae33c2b7d949454","410550665601a8abe8935f7b55d5732fe4c4224f") +-Mapping("04b88a9eba8abbac87eddcb2998beea09589c2c9","b405aa2d0301c5fc448299501278ae2db4e15e50") +-Mapping("ff15e9670843f8bd6b54ab1b042d2095b4c0aa6d","92bc35f7b6cb4232be5ac4cc031202c7ad82260b") +-Mapping("4bb6b4a5ed1cd377c5cfd97721ad12f52e63dd41","c5d18600ef3c5e795c4133cfd91a1df088f2252e") +-Mapping("9b91b9c10e3c87ed333a1e34c4f46ed68f1eee06","edb5214b29cd7de06dd10f673986d38e568b077c") +-Mapping("4f20caa6258d4c74ce6b316fd347e3efe81cf557","ea43e5e21d8aa61e00124f634a71325e6d3bfaa8") +-Mapping("5d04ce67fd14538d03fa47a2598f80d49fd564c6","df7d9f383848dcb31a2f94bb1df5270ea21aff4b") +-Mapping("e55d3f9c5213fe1a25366450127bdff67ad1eca2","fff822fead6249671cbcb090b24bce58fab38de0") +-Mapping("54b7d21f59a363e53eb1c31d76b40af2ff99321c","61150353bf9cc415f4554a9b4851c14e4255329f") +-Mapping("f5230fbf76bafd86ee4376a0e26e551df8d17fec","30e49a9ead550551e879af64ba91a0316da1c422") +-Mapping("5db778affee7c6600c8e7a177c48282dab3f6292","5304511fbc1f9a0c7340f7f0d037aa4dd13a588f") +-Mapping("107896c32d5dda4db508968ff34997a39d286966","ab8995bbca73be761402585ead491111163c44d6") +-Mapping("caca2121ffe4cb47d8ea2d9469c493995f57e0b5","68f2934a154abac9a2af72c55e4c08277172e087") +-Mapping("9b9d2aff8de4d499b4ba7ca406e000f8d3754ea7","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("9d78d1d02761b906038ba4d54c5f3427f920f5fb","56d288fa46e04cd5faf53d369a1a640a97e2bb08") +-Mapping("257becbfe4987d1f7b12af5a8dd5ed96697cd2e8","8cef65fde3f92a84218fc338de6ab967fafd1820") +-Mapping("4007d4ef26eab44bdabc2b7574d032152264d3ad","4436c9d35498e7ae3da261f6141d6d73b915e1e8") +-Mapping("45d050cde277b22a755847338f2acc2c7b834141","5768385615c61f6c9d63dccfb3548812f1ba1320") +-Mapping("bc2e84ca0939b73fcf1768209044432f6a15c2e5","c5d18600ef3c5e795c4133cfd91a1df088f2252e") +-Mapping("41f41b2354778375dc72f7ed1d9323626580dc4d","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("823ff8cf1397a5772b1f6954b60576202bf91836","83980aca2086e5c4dca5aae9a92a065a9ff4ac56") +-Mapping("f76ecd0668fcdb289456cdc72a39ad15467cc454","8cef65fde3f92a84218fc338de6ab967fafd1820") +-Mapping("0862458dad90a0d80827e22e3f86e33add6d847c","ecef6c7c809eba2a4eed5e281f19ab7331998c6f") +-Mapping("f509b26a7730d721ef87423a72b3fdf8724b4afa","5d90154886039ddbd7c1b8bf4cc273b774b14ec7") +-Mapping("fde692739576089729885b7f79aa2232cb9778c5","0506789014f9aef9ffac7d7d1e22fa72c7b85ab7") +-Mapping("72b2bd55edbb1e63a930c5ddd08b25e4f9044786","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("834bc5650acf7019a53b409db68986857822812c","b3e0d272af149c4126f90a0262d796d7401ba7a1") +-Mapping("c5a96fb7973649807a7943e7395456db158dcab6","cf04ae54e680c0b28e8311459cb8fd11315485a0") +-Mapping("770bd3d1d03f0de2e27b1ae6a0604597d0e26f84","2c31b45ae878b821975c4ebd94cc1e49f6073fd0") +-Mapping("5e8897b7b51636f157630e6639b711d698e1d101","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("c8ea4ace9213ae045123fdfeb59d1ac887656d31","92bc35f7b6cb4232be5ac4cc031202c7ad82260b") +-Mapping("48840618382eccb8a799320c8e5d08e3b52f4c42","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("c919f490bbcd2b29b74016101f7ec71aaa24bdbb","11ce918c75b05d065ce3bf98b20d62465b5afc55") +-Mapping("0eb878d2aa6e3a1cb315f3f328681b26bb4bffdb","7c84ba112429eb9bc0b99a6fe32a453c920a764c") +-Mapping("e37a13cc3594004663738bd18d8100e6db9666cf","ea43e5e21d8aa61e00124f634a71325e6d3bfaa8") +-Mapping("3712e11a828af2eea273a3e7300115e65833fbc5","5768385615c61f6c9d63dccfb3548812f1ba1320") +-Mapping("abc3073c92df034636a823c5382ece2186d22b9e","b3e0d272af149c4126f90a0262d796d7401ba7a1") +-Mapping("a73c2e555c26ef0c8b98c91c97a7d24b7017267f","410550665601a8abe8935f7b55d5732fe4c4224f") +-Mapping("53712f8637dbe326df569a90814aae1cc5429710","413ab57c0210ecbe92298c53ec4e1e39f97e4e4c") +-Mapping("664fcd3f046e2a6824602da0fad81e3e2bb0d409","05fc7faacb7c33eaad6614f62a7d560b0d2660a5") +-Mapping("45127211566c53bac386b66909a830649182ab7a","05fc7faacb7c33eaad6614f62a7d560b0d2660a5") +-Mapping("23744c84d9c0f8e4e870edb983f1ad6d33449c34","353df59893f4dc249f06047dca659b5b2172063f") +-Mapping("1dd1884891636d0eb51157d137230076bcf20627","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("4bd32c98047a809ba5fd1fac2aa044638e5f2105","05fc7faacb7c33eaad6614f62a7d560b0d2660a5") +-Mapping("e3cebcb3bd4ffaf86bb0cdfd2af5b7e698717b01","04f0d309dcbaa8425c702d1439592b87fff0a69e") +-Mapping("d6953df14657f5932270ad2b33bccafe6f39fad4","471dd52d7710dcad5fec0cd731b836b02ba4a8f4") +-Mapping("1eaadebb3dee31669c7649b32747381d11614fae","5acb7f198fa56943a2837583d555896badb5733d") +-Mapping("cfc572cae2d1fc381cce476b5c787fd7221af98c","2c31b45ae878b821975c4ebd94cc1e49f6073fd0") +-Mapping("4a8c5b20c7772bc5342b83d4b0696ea216ef75a7","e697ffbbcb41559c8de3ca3b94f3b9467e662a19") +-Mapping("97e58c0d32bcb8730f8246d25f3d2fa8092b450a","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("6d0e58bff88f620c1a4f641a627f046bf4cde4ad","df7d9f383848dcb31a2f94bb1df5270ea21aff4b") +-Mapping("0cd7ff7ddfb75a38dca81ad3e76b1e984129e939","5304511fbc1f9a0c7340f7f0d037aa4dd13a588f") +-Mapping("a74d1862d4d87a56244958416fd05976c58ca1a8","05fc7faacb7c33eaad6614f62a7d560b0d2660a5") +-Mapping("d9a105fdd46c926ae606777a46dd90e5b838f92f","bdaa76cfde64d06bb93c1f9102a0312d84cd0983") +-Mapping("beac68a88711a90346ec8b68e3baefbec62b3b0d","7c84ba112429eb9bc0b99a6fe32a453c920a764c") +-Mapping("421bd77f42c2fe8a2596dbcc1580ec97fb89009f","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("f68e08933d8f519a9655934fedebbc509661b219","9fe551ae49289ce6f693ca0dabf4c9c15164f67d") +-Mapping("95f437b3cfb2fec966d7eaf69d7c2e36f9c274d1","e697ffbbcb41559c8de3ca3b94f3b9467e662a19") +-Mapping("da305a2b00530aa34dea4e48389204c26fa35dbb","0506789014f9aef9ffac7d7d1e22fa72c7b85ab7") +-Mapping("760ce94c69ca510d44087291c311296f6d9ccdf5","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("792c645ca7d11a8d254df307d019c5bf01445c37","a7749fe451c37ec192b282ec7303b9809b49df93") +-Mapping("6d3f4e0aab3e36ceb8b83d1e9467514685f6b751","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("803c60218ffac3384b0063c1b87ae7944163bba7","8cef65fde3f92a84218fc338de6ab967fafd1820") +-Mapping("0d0f6b113047b2cf9afbde990cee30fd5b866469","0af3bd01dfae488392dc6f08daa2d0d8d370fb00") +-Mapping("67100f61e62a86f2bf9e38552ee138e231eddc74","6276c135d185e8492e8a2b9db5ca04e51c3293fa") +-Mapping("2477e2493e67527fc282c7239e019f7ebd513a1a","e697ffbbcb41559c8de3ca3b94f3b9467e662a19") +-Mapping("b2e36e6c2d229126b59e892c9147fbb68115d292","5768385615c61f6c9d63dccfb3548812f1ba1320") +-Mapping("2748a9fd93dd1a00a4521f4f16de5befbf77f6cd","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("b1af43bc63bc7417938df056f7f25d456cc11b0e","de597fca40d129435c53a69c6662d7bfac29771d") +-Mapping("06e47688bf15d0215edbe05b21603062f6d2eb5d","fff822fead6249671cbcb090b24bce58fab38de0") +-Mapping("f98721f886ab52d32d622ad0a46216ad03f3e525","ab8995bbca73be761402585ead491111163c44d6") +-Mapping("4f4656d46d84a488ae3df34b08f362d7071036a0","410550665601a8abe8935f7b55d5732fe4c4224f") +-Mapping("5c9e5df3a097e094641f16dab501ab1c4da10e9f","3cecd6003b3eb15168421084a27223596517899c") +-Mapping("a4cbb44ae2c80545db957763b502dc7f6ea22085","cf04ae54e680c0b28e8311459cb8fd11315485a0") +-Mapping("ef663a8a48ea6b98b43cbfaefd99316b36b16825","c9e5e6a53aef5cd1b939ecfa18f56bdf5bf0451c") +-Mapping("a9dd56ff9a08d74c53d5cc22d18f126a12749608","4646a88b7a1e68326d092b9cbbbbdd616a51077f") +-Mapping("518deda77feb4957bfd311b6cb50baa7ef9ca6a2","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("25d8a9494ca6d77361e47c1505ecf640b168819e","413ab57c0210ecbe92298c53ec4e1e39f97e4e4c") +-Mapping("e3051d8c24467b54c81da9d9ad70a3e82e106ec1","5acb7f198fa56943a2837583d555896badb5733d") +-Mapping("5d04957a4b4714f71d38326fc96a0b0ef6dc5800","db4a97c4cbcb160b3754c803284dd0110d1de1e4") +-Mapping("83e4eed16ef7adb54a802e3b684427e0e912c2b7","c5d18600ef3c5e795c4133cfd91a1df088f2252e") +-Mapping("edc02580e4e80476ac1ded2cc1008eaf8b8400e6","5768385615c61f6c9d63dccfb3548812f1ba1320") +-Mapping("9c09c1f7cfcf9de0522bcd1cfda32b552195c464","eefec8abda7cb8e8693aa876fbd1e21f2a6a5c2d") +-Mapping("8a87b945b27b5670ac5ed665bbb0fccc1b88a0a0","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("534b42394d743511db1335d5ed08d507ab7c6e73","dad56c39474377c7d47e261b380d0be3aed104cc") +-Mapping("ef92009c1dbe2750f1d24a6619b827721fb49749","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("c4715198b50d1cdaad44b6e250844362b77dcdd7","9ff52752d855722c55dbc71d9b22bd42eabfc468") +-Mapping("3fc30d884ae0c988d98452a06737705cfe34806a","5b5196ad65db877c2f140dfc7a25f3fc6f2e40c6") +-Mapping("698fcd38fa9548e64a2092ff48c9d15ceb57d40c","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("ffe52882ed79be67344dd6085559e308241e7f60","56d288fa46e04cd5faf53d369a1a640a97e2bb08") +-Mapping("853c4774e26ea97b45fe74de9a6f68e526784323","08f2904dfaf5e75fbcc1305c8b0aad5fae71a4ff") +-Mapping("603ab5bd6e0ffefafa7411cd8bd23a6ca82bcff0","30e49a9ead550551e879af64ba91a0316da1c422") +-Mapping("fa416394275d2468d104b8f72ac31b1ddf7ee52e","8cef65fde3f92a84218fc338de6ab967fafd1820") +-Mapping("826cb062a659f7b719a8a0ab1497a78229318aab","ec2826cc2e0b3a800836bcf8733dee0924f6b7ab") +-Mapping("f44c6e4e288e4f49c5c257b2e2cb2ad5918f26a3","6f4681bacc78a00a63766f12a17560701ab5c1e8") +-Mapping("c2de47a9aa4c9812884f341f1852e9c9610f5f7a","0506789014f9aef9ffac7d7d1e22fa72c7b85ab7") +-Mapping("f05a5240440b3eaef1684a7965860fab40301947","fb1aa5624dff1d96249080fe365ed794431f45db") +-Mapping("d4e3570db4c007089035b833cc20c7fc2f8cb32f","410550665601a8abe8935f7b55d5732fe4c4224f") +-Mapping("b5a3341f1b8b475990e9d1b071b88d3c280936b4","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("769d12eec1d0bc3708841dfc149d3ec98b04bec6","05fc7faacb7c33eaad6614f62a7d560b0d2660a5") +-Mapping("442ae7f04026c215a03b155eaaf9cde8bb5cf02a","df7d9f383848dcb31a2f94bb1df5270ea21aff4b") +-Mapping("8dae8cdcc8fa879cea6a4bbbfa5b32e97be4c306","de597fca40d129435c53a69c6662d7bfac29771d") +-Mapping("a0d664bae6ca79c54cc054aa2403198e105190a2","bdaa76cfde64d06bb93c1f9102a0312d84cd0983") +-Mapping("f3c923a13a458c35ee26b3513533fce8a15c9c05","9fe551ae49289ce6f693ca0dabf4c9c15164f67d") +-Mapping("8ac1525e091d3db28e67adcbbd6db1e1deaa37fb","5304511fbc1f9a0c7340f7f0d037aa4dd13a588f") +-Mapping("bc0e288ad02ef362b5a6c42aaf61f2901c9b46db","5b5196ad65db877c2f140dfc7a25f3fc6f2e40c6") +-Mapping("4760b8fb886a3702ae11bfa7868d495b2675b5ed","5acb7f198fa56943a2837583d555896badb5733d") +-Mapping("0820e54a8ad7795d7b555b37994f43cfe62356d4","471dd52d7710dcad5fec0cd731b836b02ba4a8f4") +-Mapping("5fd2f06e99a985dd896684cb2c9f8c7090eca1ab","05fc7faacb7c33eaad6614f62a7d560b0d2660a5") +-Mapping("e15510ca33ea15c893b78710101c962b11459963","dad8e11e9fcbd76c0a2dc47211dcd654effed010") +-Mapping("3360cc3a0ea33c84d0b0b1163107b1c1acbf2a69","5768385615c61f6c9d63dccfb3548812f1ba1320") +-Mapping("37538aa1365d1f8a10770a7d15c95b3167c8db57","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("8a58268b5ad9c4a240be349a633069d48991eb0c","b405aa2d0301c5fc448299501278ae2db4e15e50") +-Mapping("6645da366eed0c61258a04265bea513e94df7ea6","bdaa76cfde64d06bb93c1f9102a0312d84cd0983") +-Mapping("8aa9d2014f4e5258f83b907e8431c59a33acdae7","df7d9f383848dcb31a2f94bb1df5270ea21aff4b") +-Mapping("f7af19c279b8b7ea3d2c21fcbd67164af8d5d968","dad56c39474377c7d47e261b380d0be3aed104cc") +-Mapping("77621317d643cc5d13da60b26ab68b057668e688","03c64bf532ceec915f74460daf5344bb8ccf23d3") +-Mapping("aa4e57ca8f18b836bf77923cd0d9ad1390f0110b","e697ffbbcb41559c8de3ca3b94f3b9467e662a19") +-Mapping("097bc6a84f2280a889b9ab4b544f27851a978927","410550665601a8abe8935f7b55d5732fe4c4224f") +-Mapping("22ee68dc586440f96b76b32fbd6087507c6afdb9","2c31b45ae878b821975c4ebd94cc1e49f6073fd0") +-Mapping("6e19f3f383b99414490243665c96b9f4e0f313f9","b03d3dc478ba13f405cf9a877a4894de096a1cc1") +-Mapping("adef9da30f1ecbfeb81312d01ed94ac53f7161ba","de597fca40d129435c53a69c6662d7bfac29771d") +-Mapping("7e6d6e5f535321c2223f044caba16f97b825009c","a7749fe451c37ec192b282ec7303b9809b49df93") +-Mapping("6dee5f1126dfd5c9314ee5ae9d9eb010e35ef257","08f2904dfaf5e75fbcc1305c8b0aad5fae71a4ff") +-Mapping("5239f5c57bb6eb9e894081727f5aba0a67e89763","05fc7faacb7c33eaad6614f62a7d560b0d2660a5") +-Mapping("fe982319aa0aa5bbfc2795791a753832292bd2ba","bdaa76cfde64d06bb93c1f9102a0312d84cd0983") +-Mapping("5c5b8afd80e6fa1d24632153cb2257c686041d41","413ab57c0210ecbe92298c53ec4e1e39f97e4e4c") +-Mapping("59947fcae6a40df12e33af8c8c7291014b7603e0","92bc35f7b6cb4232be5ac4cc031202c7ad82260b") +-Mapping("a1947b3f9e2831e2060bc42f0c78e4a2bb67930a","9fe551ae49289ce6f693ca0dabf4c9c15164f67d") +-Mapping("a7f28678bbf4e16893bb6a718e427504167a9494","b94e59cc41f8eeb36ee269cae3275d7620189c14") +-Mapping("c43753f910aae000f8bcb0a502407ea332afc74b","b94e59cc41f8eeb36ee269cae3275d7620189c14") +-Mapping("1423bec54cf2db283b614e527cfd602b481485d1","e697ffbbcb41559c8de3ca3b94f3b9467e662a19") +-Mapping("ed084b0b8341c974769a0328f61851b0e1fc17fa","05fc7faacb7c33eaad6614f62a7d560b0d2660a5") +-Mapping("ed33453a37d602f34cc40c205f9b9b8a8aff88b5","75b27ef59cd0eb95b50d0cde14b05e0079b3ebe9") +-Mapping("2daa404e9a151a2e8262cbd6d8c209fd067aca16","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("b1496c6e606dd908dd651ac2cce89815e10d7fc5","5acb7f198fa56943a2837583d555896badb5733d") +-Mapping("8970e8bcf6153d1ead2283f1a0ed7b192230eca6","05fc7faacb7c33eaad6614f62a7d560b0d2660a5") +-Mapping("dbb73f8f79ab176a897d5a95e696adb71b957cbe","9fe551ae49289ce6f693ca0dabf4c9c15164f67d") +-Mapping("39d5a61f2e4e237123837f5162cc275c2fd7e625","3cecd6003b3eb15168421084a27223596517899c") +-Mapping("118b50524b79e565f017e08bce9b90a16c63634f","ec2826cc2e0b3a800836bcf8733dee0924f6b7ab") +-Mapping("aa69777ea2902208b24b3fd77767d577ceaf6386","e697ffbbcb41559c8de3ca3b94f3b9467e662a19") +-Mapping("07e0e2ec268c140e607e1ac7f49f145612d0f597","a42e62fa0a59d0ba620889f97513929a113a6fbd") +-Mapping("2d8bd9b74dc0cf06d881bac645698ccbcf9d9c5e","fff822fead6249671cbcb090b24bce58fab38de0") +-Mapping("61d9231ff2604a0467987042d9ebf9ff9ea739b5","df7d9f383848dcb31a2f94bb1df5270ea21aff4b") +-Mapping("80fc9b0ecb29050d45b17c64af004200afd3cfc2","d9cd4a33f53689bc0847775669a14f666a138fd7") +-Mapping("4253153db205251f72ea4493687a31e04a2a8ca0","4e27ed3af19e604d7b65e130145fcecdc69fba7a") +-Mapping("537ccdf3ac44c8c7a8d36cbdbe6fb224afabb7ae","08f2904dfaf5e75fbcc1305c8b0aad5fae71a4ff") +-Mapping("3503f565e1fb7296983757d2716346f48a4a262b","5304511fbc1f9a0c7340f7f0d037aa4dd13a588f") +-Mapping("7402a394471a6738a40fea7d4f1891666e5a80c5","9fe551ae49289ce6f693ca0dabf4c9c15164f67d") +-Mapping("9b88e0a8667040452a94fda8548f0f5f0f801f90","a7749fe451c37ec192b282ec7303b9809b49df93") +-Mapping("17eec1433c69972844dd228b5fe801f218e118c3","8cef65fde3f92a84218fc338de6ab967fafd1820") +-Mapping("9e346646e93cc243567e27bb0f4e8716d56ad1f1","5b5196ad65db877c2f140dfc7a25f3fc6f2e40c6") +-Mapping("75208942f6144daac669e8e382029fc33bdce841","03c64bf532ceec915f74460daf5344bb8ccf23d3") +-Mapping("6a91782b72fca586b15ba68364bc7baab837af86","dad56c39474377c7d47e261b380d0be3aed104cc") +-Mapping("eeba189cfb2cfc5c5898513352d4ca8f1df06e05","edb5214b29cd7de06dd10f673986d38e568b077c") +-Mapping("2d03399f53d28a8be645625376c0c9fbe601a01d","ecef6c7c809eba2a4eed5e281f19ab7331998c6f") +-Mapping("6c8927b0cf80ceee19386026cf9d7fd4fd9d486f","471dd52d7710dcad5fec0cd731b836b02ba4a8f4") +-Mapping("b32e6e6ac8921035177256ab6806e6ab0d4b9b94","8cef65fde3f92a84218fc338de6ab967fafd1820") +-Mapping("e9920ef7749d11fc71cc32ca4ba055bcfeaab945","410550665601a8abe8935f7b55d5732fe4c4224f") +-Mapping("8f349be27815d43d462a32faeb270a22a68486b6","ab8995bbca73be761402585ead491111163c44d6") +-Mapping("368275062fb655c1f36e0398f88b15379a1f3c93","410550665601a8abe8935f7b55d5732fe4c4224f") +-Mapping("7979016aff545f7b41cc517031026020b340989d","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("20cc75272619cc452e3ae6c131e61974f6aa9929","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("8a79d08fa57e1c257d647c9848e35defcb379c07","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("088b987307b91612ab164026e1dcdd0129fdb62b","390f717a0af5851271792da9ff235c95f3db2556") +-Mapping("6e87bacd37539b7e7cd75152dffd225047fa983a","2c31b45ae878b821975c4ebd94cc1e49f6073fd0") +-Mapping("dd67187965e136bff1ed05e035293441c60f0790","5d90154886039ddbd7c1b8bf4cc273b774b14ec7") +-Mapping("f82664191d0e8764b7435b9d72eb0e366b8b1464","db4a97c4cbcb160b3754c803284dd0110d1de1e4") +-Mapping("cd2cd4c9627e52c33e68e8c93a8916dc11094cbb","c5d18600ef3c5e795c4133cfd91a1df088f2252e") +-Mapping("0176a9eef845e7421b7e2f7ef015333a41a7c027","df7d9f383848dcb31a2f94bb1df5270ea21aff4b") +-Mapping("eceec57f72150dd548e05025a05a93381da41385","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("d7f94516345a36ddfcd68cbdf1df835d356795c3","8d470b57968fd875c2d9ce50446868b906f54752") +-Mapping("94d346360da50f159e0dc777dc9bc3c5b6b51a00","5768385615c61f6c9d63dccfb3548812f1ba1320") +-Mapping("8b4085359ae798dedb05c95ad42520557bd25320","65bdf79da3f72269e6fe7aac1355df1420613889") +-Mapping("7760cd0fbbbf2c59a625e075a5bdfa88b8e30f8a","df7d9f383848dcb31a2f94bb1df5270ea21aff4b") +-Mapping("a7eff79135de09a49b50acb029925275a7b42ccb","2c31b45ae878b821975c4ebd94cc1e49f6073fd0") +-Mapping("dfd43f0fdd4e6969c7d82c0670d70bf305fbccf8","1b946106b7955d3dcde26719b9b62a5a2c4b78fe") +-Mapping("47c3158c3d797f75f0f7b2b2a977179668919dab","ec2826cc2e0b3a800836bcf8733dee0924f6b7ab") +-Mapping("ce93331e2cf21ac4b72a53854b105955919114e7","5768385615c61f6c9d63dccfb3548812f1ba1320") +-Mapping("b543afca9b90ad6e4689b6d613ab51f9d3ba15e7","08f2904dfaf5e75fbcc1305c8b0aad5fae71a4ff") +-Mapping("07194ffcd25b0871ce560b9f702e52db27ac9f77","410550665601a8abe8935f7b55d5732fe4c4224f") +-Mapping("7e11379f3b4c376fbb9a6c4d44f3286ccc28d149","353df59893f4dc249f06047dca659b5b2172063f") +-Mapping("66bf391c3aabfc77f5f7139fc9e6944f995d574e","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("b48cafd9eb658b5d74015ddbe5335c3842a03a63","bdaa76cfde64d06bb93c1f9102a0312d84cd0983") +-Mapping("22bc9e1d9ca49ee4f5cd953088ab09c238a6dd26","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("10a52c25cad963986cace7a22c167363afca0d74","e697ffbbcb41559c8de3ca3b94f3b9467e662a19") +-Mapping("ceedf1d5febd65b012b8bcd513d70a0a6a091210","2c31b45ae878b821975c4ebd94cc1e49f6073fd0") +-Mapping("2113659479a82ea69633b23ef710b58ab127755e","03c64bf532ceec915f74460daf5344bb8ccf23d3") +-Mapping("e708cbd91c9cae4426d69270248362b423324556","410550665601a8abe8935f7b55d5732fe4c4224f") +-Mapping("4a8b6f708c38342a6c74aa00cf4323774c7381a6","ab8995bbca73be761402585ead491111163c44d6") +-Mapping("710a362dc7634fce42885327b6b7b1b3a9b0c41a","4436c9d35498e7ae3da261f6141d6d73b915e1e8") +-Mapping("51748a8fc77283914d4135f31b5966a407208187","68f2934a154abac9a2af72c55e4c08277172e087") +-Mapping("e649e903440bfd919bfc9db848c28df6d795a116","b94e59cc41f8eeb36ee269cae3275d7620189c14") +-Mapping("22ddcd1a13082b7be0fc99b720677efd2b733816","9abd746a327320048ae2b212f34edcadbcafcadf") +-Mapping("eb4fc71dc9024f15a0c9cc44bcc10c861e9d585e","8cef65fde3f92a84218fc338de6ab967fafd1820") +-Mapping("a5fb9ae5b2ed3cb011ada9dc1e8633aa0927f279","03c64bf532ceec915f74460daf5344bb8ccf23d3") +-Mapping("202720bf483088dbdb343f78c0aa77067fdd8156","9abd746a327320048ae2b212f34edcadbcafcadf") +-Mapping("c59199efca5856cdf810919fbf9b5bce32dc4523","0af3bd01dfae488392dc6f08daa2d0d8d370fb00") +-Mapping("3a5d45f68cadc8fff4fbb557780f92b403b19c19","ab8995bbca73be761402585ead491111163c44d6") +-Mapping("96bb8b31c81dc2394317f2f083c3acf8087efea1","7c84ba112429eb9bc0b99a6fe32a453c920a764c") +-Mapping("1fd5b9d516c035a898dcb437b2f982bea5d4bc88","9fe551ae49289ce6f693ca0dabf4c9c15164f67d") +-Mapping("31ee872db5aae4750e3da1ca4ed1523c4356947f","56d288fa46e04cd5faf53d369a1a640a97e2bb08") +-Mapping("702b45e409495a41afcccbe87a251a692b0cefab","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("0edce6f4bbb4514482537f569f0b8ef48e71e0a0","8cef65fde3f92a84218fc338de6ab967fafd1820") +-Mapping("e160e5cb80652bc2afe74cb3affbe35b74243ea9","de597fca40d129435c53a69c6662d7bfac29771d") +-Mapping("1fa54ad9680cc82e7301f8ed4e9b7402dfd6ce0e","3cecd6003b3eb15168421084a27223596517899c") +-Mapping("f1b882b55805c342e46ee4ca3beeef1d1fa2044b","413ab57c0210ecbe92298c53ec4e1e39f97e4e4c") +-Mapping("6a889570e46c03d7b156ec08f3f4cb4d145924a3","bdaa76cfde64d06bb93c1f9102a0312d84cd0983") +-Mapping("dd927a5b0f29342f7ad919fb52ca29510d2e7362","05fc7faacb7c33eaad6614f62a7d560b0d2660a5") +-Mapping("fdc0011561c6365c596dfd8fa1ef388162bc89c7","4436c9d35498e7ae3da261f6141d6d73b915e1e8") +-Mapping("b520af6fd515b186caed436d75162a42aa183d95","e697ffbbcb41559c8de3ca3b94f3b9467e662a19") +-Mapping("83b30a639d5abd1270ade35d9bd92271f5a5ba18","250eeb4c3c00b7831226cf5266aacb5fca1e13f3") +-Mapping("273f42b5964c29dda2c5a349dd4655529767b07f","04f0d309dcbaa8425c702d1439592b87fff0a69e") +-Mapping("623fb90b5a1f324e0ec44085116bf858cef19a00","65bdf79da3f72269e6fe7aac1355df1420613889") +-Mapping("da384694807172f0ca40eca2e49a11688aba6e93","bdaa76cfde64d06bb93c1f9102a0312d84cd0983") +-Mapping("7ced01a730e8fc1bae2f8d4369c26812c0484da4","fb1aa5624dff1d96249080fe365ed794431f45db") +-Mapping("9b98af84c4aa66392236fff59c86da2130d46d46","f7256d28d1c2f8340ab5b99df4bdb15aa232f3f3") +-Mapping("a15f484b918a4533ad633ea903ccce82910af342","c26a8bbd6d0e7bbfa2891934a1af2934cab3b6bb") +-Mapping("0f0c640e0ee5a9ad365e78e3c62239b3d65b7045","413ab57c0210ecbe92298c53ec4e1e39f97e4e4c") +-Mapping("75cf41afb468152611212271bae026948cd3ba46","7c84ba112429eb9bc0b99a6fe32a453c920a764c") +-Mapping("0f6f2d681b39c5f95459cd09cb936b6ceb27cd82","b777552167d2651ceb13437f9fde4dca95045912") +-Mapping("76e83339bb619aba206e5590b1e4b813a154b199","7a5d3abfb1aa3a38e0b3b3508c760fc8e712226c") +-Mapping("3ebcfa1451cfedc13a07e6353d8ade9742dfdc2a","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("d6eaea1c8860adb5302d2fbaad409e36585ab217","ab8995bbca73be761402585ead491111163c44d6") +-Mapping("b2025326088b54fb3f083bebeba14e0a15bf00d3","56d288fa46e04cd5faf53d369a1a640a97e2bb08") +-Mapping("5e7af4669f80e5f682141f050193ab679afdb4b1","df7d9f383848dcb31a2f94bb1df5270ea21aff4b") +-Mapping("1389494ac145a84dba025ff65969f7ab150c3f02","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("0b680cfce544ff9a59d720020e397c4bf3346650","c5d18600ef3c5e795c4133cfd91a1df088f2252e") +-Mapping("e82734e56b2a50d38e0937d08f559d15dbe8e46b","5768385615c61f6c9d63dccfb3548812f1ba1320") +-Mapping("bc39d4d9c514e5fdb40a5782e6ca08924f979c35","ce48709405270cae2dfdf99d9a8d57a4f672ad34") +-Mapping("18f3be7704a4ec7976fcd1272c728974243d29bd","2c31b45ae878b821975c4ebd94cc1e49f6073fd0") +-Mapping("fc23a81831d5b41510d3261c20c34dd8d32f0f31","df7d9f383848dcb31a2f94bb1df5270ea21aff4b") +-Mapping("5ef299eb9805b4c86b227b718b39084e8bf24454","471dd52d7710dcad5fec0cd731b836b02ba4a8f4") +-Mapping("d8878868c8d7ef3779e7243953fc050cbb0e0565","05fc7faacb7c33eaad6614f62a7d560b0d2660a5") +-Mapping("e38fb306b7f5e65cca34df2dab1f0db15e1defb4","ce48709405270cae2dfdf99d9a8d57a4f672ad34") +-Mapping("9d09331e00b02f81c714b0c41ce3a38380dd36a2","5304511fbc1f9a0c7340f7f0d037aa4dd13a588f") +-Mapping("69656fa4cbafc378fd63f9186d93b0df3cdd9320","c5d18600ef3c5e795c4133cfd91a1df088f2252e") +-Mapping("d1aed50ab81df3140977c610c5a7d00f36dc519f","9abd746a327320048ae2b212f34edcadbcafcadf") +-Mapping("9722952f0bed5815cb22cb4878be09fb39f92804","77f333b304424ae63dc70e10c6676dd645230f94") +-Mapping("38114ff16e7856f98b2b4be7ab4cd29b38bed59a","276b54e9c930c4ff015e1958ad1c640deffd29b2") +-Mapping("6bdae9edd0cc099daa6038bca469dc09b6fc078a","56d288fa46e04cd5faf53d369a1a640a97e2bb08") +-Mapping("7f9c43cf98cfe1c369045399929cb098155b8374","8cef65fde3f92a84218fc338de6ab967fafd1820") +-Mapping("5099914a16a215794ad243df0cc7a05d91d168e0","9fe551ae49289ce6f693ca0dabf4c9c15164f67d") +-Mapping("71c7e149e42cb0fc78a80db70d2525973311d488","df7d9f383848dcb31a2f94bb1df5270ea21aff4b") +-Mapping("6767d9b90b6b630ad8e2a9e5e02fd74c00c98759","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("71f8d0c8f1060bbe74100f29cc6f2da63d697c28","2c31b45ae878b821975c4ebd94cc1e49f6073fd0") +-Mapping("1bd30ce2aac40c7698aa4a1b9520aa649ff2d1c5","413ab57c0210ecbe92298c53ec4e1e39f97e4e4c") +-Mapping("3a7dfda40a3e798bf086bd58cc7e5e09deb808b5","05fc7faacb7c33eaad6614f62a7d560b0d2660a5") +-Mapping("1057dc97afce39ff6a224966ece3ed438af4c1f5","73c3a496cc8ce261e87abbd998b36ab16dab4f4b") +-Mapping("bf4342114e357f2934d59e12e31e94532ddb2adf","6f4681bacc78a00a63766f12a17560701ab5c1e8") +-Mapping("de521cbb303c08febd9fa3755caccd4f3e491ea3","dad8e11e9fcbd76c0a2dc47211dcd654effed010") +-Mapping("beb5ae474d2835962ebdf7416bd1c9ad864fe101","de597fca40d129435c53a69c6662d7bfac29771d") +-Mapping("99b89533d4cdf7682ea4054ad0ee36c351d05df1","92bc35f7b6cb4232be5ac4cc031202c7ad82260b") +-Mapping("1773f60ea5d42e86b8fdf78d2fc5221ead222bc1","77f333b304424ae63dc70e10c6676dd645230f94") +-Mapping("898f36c83cc28d7921a1d7b3605323dc5cfcf533","62e86b42b5ed342d30c539e22810c26d312995e2") +-Mapping("1700ca07c6dd7becff85678409a5df6ad4cf4f47","b777552167d2651ceb13437f9fde4dca95045912") +-Mapping("74bd074eefcf4915c73d1ab91bc90859664729e6","08f2904dfaf5e75fbcc1305c8b0aad5fae71a4ff") +-Mapping("8a6518427e11e6dd13d6f39663b82eb4f810ca05","ce48709405270cae2dfdf99d9a8d57a4f672ad34") +-Mapping("36f1f04f18b89ba4a999bcfd6584663fd6fc1c5d","ab8995bbca73be761402585ead491111163c44d6") +-Mapping("2c462a2f776b899d46743b1b44eda976e846e61d","df7d9f383848dcb31a2f94bb1df5270ea21aff4b") +-Mapping("4b65a86ebace8600c8e269e8bfe3365cdc460e68","c5d18600ef3c5e795c4133cfd91a1df088f2252e") +-Mapping("481068a707679257e2a738b40987246e0420e787","c5d18600ef3c5e795c4133cfd91a1df088f2252e") +-Mapping("b497e18995d6b6992f97512c6b86b5cb3f2f34f5","e697ffbbcb41559c8de3ca3b94f3b9467e662a19") +-Mapping("bbebe7351fcd29af1eb9a35e315369b15887ea09","471dd52d7710dcad5fec0cd731b836b02ba4a8f4") +-Mapping("4cf7673076e6975532213e494dd3f7f9d8c2328e","dad56c39474377c7d47e261b380d0be3aed104cc") +-Mapping("3e826bb11228508fbe749e594038d6727208aa94","c26a8bbd6d0e7bbfa2891934a1af2934cab3b6bb") +-Mapping("c97f11af7bc4a6d3578f6a953be04ab2449a5728","0506789014f9aef9ffac7d7d1e22fa72c7b85ab7") +-Mapping("f93bb2a50b37bc8bafe4d960e2afd839eaa854ed","05fc7faacb7c33eaad6614f62a7d560b0d2660a5") +-Mapping("8e18e26f12b1e8b3e913b15278bf6185f0f61add","5768385615c61f6c9d63dccfb3548812f1ba1320") +-Mapping("cd1ef390e731ed77b90b11b1f77e2c5ca641b261","9bb2a50e04460fff646830502d575b82dbf17055") +-Mapping("b0e40bfba44836ad30051ffb077c1cfc5bf4a59f","9ff52752d855722c55dbc71d9b22bd42eabfc468") +-Mapping("daecab3a784f28082df90cebb204998051f3557d","5304511fbc1f9a0c7340f7f0d037aa4dd13a588f") +-Mapping("c8915eebeaaef9f7cc1cff6ffd97f578b03c2ac9","0506789014f9aef9ffac7d7d1e22fa72c7b85ab7") +-Mapping("81dc88f88f92ba8ad7465f9cba10c12d3a7b70f1","a7749fe451c37ec192b282ec7303b9809b49df93") +-Mapping("1c389ffeff814726dec325f0f2b0c99107df2673","bdaa76cfde64d06bb93c1f9102a0312d84cd0983") +-Mapping("da3629b05f8f1b425a738bfe9fe9aedd47c5417a","4646a88b7a1e68326d092b9cbbbbdd616a51077f") +-Mapping("119307a83e12291a3fc126735d6bd0292c443464","4646a88b7a1e68326d092b9cbbbbdd616a51077f") +-Mapping("476acbf1e9965b5e95c90f0d7d658709812b7003","bc5669eef8c1d747e82694547fd57a1400a5afec") +-Mapping("bb1fbbf84455fbad9afd26c17e0f725019322655","8cef65fde3f92a84218fc338de6ab967fafd1820") +-Mapping("f0f68778f798d6d34649745b41770829b17ba5b8","2c56ea38b045624dc8b42ec948fc169eaff1206a") +-Mapping("9310e3bd4f425f84fc27878ebf2bda1f30935a63","05fc7faacb7c33eaad6614f62a7d560b0d2660a5") +-Mapping("9af17757be1cc3f672928ecf06c40a662c5ec26d","1b946106b7955d3dcde26719b9b62a5a2c4b78fe") +-Mapping("9ae6cedb8d1e37469be1434642a3e403fce50a03","260514da942f281bc2dc3b14b629d3e660b3484f") +-Mapping("311376d30dc1cfa622142a9f50317b1e0cb4608a","04f0d309dcbaa8425c702d1439592b87fff0a69e") +-Mapping("80184183ba0a53aa4f491753de9502acd3d6920c","0506789014f9aef9ffac7d7d1e22fa72c7b85ab7") +-Mapping("a647c0cd68bdd0f15081019f0b21bc31ae23f072","fff822fead6249671cbcb090b24bce58fab38de0") +-Mapping("f4fbb93113aa4f0a0cd08e74afb35381bbfbc7f0","fff822fead6249671cbcb090b24bce58fab38de0") +-Mapping("23adf9fd843da7a3394c824b056f93151aaa40ad","410550665601a8abe8935f7b55d5732fe4c4224f") +-Mapping("412f43ac5b4ae8c3599e71c6972112e9be4758fa","413ab57c0210ecbe92298c53ec4e1e39f97e4e4c") +-Mapping("8876ffc9235dade728e1fbc4be4c85415fdd0bcd","c9e5e6a53aef5cd1b939ecfa18f56bdf5bf0451c") +-Mapping("74f7e32f43b5fb0f83896d124566d8242eb786b1","77f333b304424ae63dc70e10c6676dd645230f94") +-Mapping("c5eae562935922f712edec56a45591bc2f8ded1c","0506789014f9aef9ffac7d7d1e22fa72c7b85ab7") +-Mapping("f4eb5d9f719cd3c849befc8914ad8ce0ddcf34ed","9abd746a327320048ae2b212f34edcadbcafcadf") +-Mapping("9703ef666123c465f784e294b5b24d6d35a37745","dad56c39474377c7d47e261b380d0be3aed104cc") +-Mapping("b2d115f6db5172c961dfeb50de15f35784dbc7c9","8d48e3bbb2da2f5eb5f4a95efd6846e9ea93a160") +-Mapping("07e968b640e8ff76fa8be4b48b70ab80ea577800","56d288fa46e04cd5faf53d369a1a640a97e2bb08") +-Mapping("449e8eaa286e407c9cd8cac655b77998fd53db6b","ec2826cc2e0b3a800836bcf8733dee0924f6b7ab") +-Mapping("f4c675c476c18b1a11041193f2f59d695b126bc8","73c3a496cc8ce261e87abbd998b36ab16dab4f4b") +-Mapping("96d07e0ac9f0c56b95a2561c6cedac0b23a5d2a3","a8c5f90b06c9bf2bfa2c2f4aedd7c395cb92195d") +-Mapping("fc2daaae610b5515438b551a2f3706196a997f35","c9e5e6a53aef5cd1b939ecfa18f56bdf5bf0451c") +-Mapping("f5f33ec0e0455eefa72fc5567eb1280a4d5ee206","db4a97c4cbcb160b3754c803284dd0110d1de1e4") +-Mapping("dfd52ba6ac2262c6b61c59ec86bfd23e4e53d3de","c5d18600ef3c5e795c4133cfd91a1df088f2252e") +-Mapping("52e3dffa50cfffdcfa145c0cc0ba48b49abc0c07","a42e62fa0a59d0ba620889f97513929a113a6fbd") +-Mapping("38048763e885a3ee139abf39d59a530b16484150","e697ffbbcb41559c8de3ca3b94f3b9467e662a19") +-Mapping("78ca1bda3522b14bc0336bc01dd1d49fdba2cda7","c5d18600ef3c5e795c4133cfd91a1df088f2252e") +-Mapping("07e0c3651ce2a7b326f7678e135d8d5bbbbe5d18","c5d18600ef3c5e795c4133cfd91a1df088f2252e") +-Mapping("17e62f77f954bed97aae839624bfd6dd68342daf","390f717a0af5851271792da9ff235c95f3db2556") +-Mapping("e792288df31636ca28108516c63a00ce4267063a","b777552167d2651ceb13437f9fde4dca95045912") +-Mapping("6184f23950fb4aa14884ce310d948dc6fca269a3","0506789014f9aef9ffac7d7d1e22fa72c7b85ab7") +-Mapping("152f6609246558be5e2582e67376194815e6ba0d","410550665601a8abe8935f7b55d5732fe4c4224f") +-Mapping("b3e19a221e63dcffdef87e12eadf1f36a8b90295","ab8995bbca73be761402585ead491111163c44d6") +-Mapping("8256379832b5ecb7f71e8c5e2018446482223c12","bdaa76cfde64d06bb93c1f9102a0312d84cd0983") +-Mapping("797fd92628842c1f5face9fb93b0fe4f1f9d297f","413ab57c0210ecbe92298c53ec4e1e39f97e4e4c") +-Mapping("ac162c6abe34cdf965afc0389f6cefa79653c63b","5b5196ad65db877c2f140dfc7a25f3fc6f2e40c6") +-Mapping("7efe1c6e678a263b9464f2e7f06f552b4d4db5a5","a8c5f90b06c9bf2bfa2c2f4aedd7c395cb92195d") +-Mapping("381b445ff5751f9f39ec672b623372dff09c276e","c9e5e6a53aef5cd1b939ecfa18f56bdf5bf0451c") +-Mapping("19bd93467617a447c22ec32cc1cf14d40cb84ccf","92bc35f7b6cb4232be5ac4cc031202c7ad82260b") +-Mapping("a8486b64b0c87dabd045453b6c81500015d122d6","c26a8bbd6d0e7bbfa2891934a1af2934cab3b6bb") +-Mapping("1836e3b42a5b2f37fd79104eedbe8f48a5afdee6","fb1aa5624dff1d96249080fe365ed794431f45db") +-Mapping("24a9bcbb7cb0d8bdc11b8252a9c13f7562c7e4ca","390f717a0af5851271792da9ff235c95f3db2556") +-Mapping("09f4c9f5082f78b0adcee83d3ab4337e000cd28e","2c31b45ae878b821975c4ebd94cc1e49f6073fd0") +-Mapping("9eae1fc0ea9b00341b8fe191582c4decb5cb86a3","edb5214b29cd7de06dd10f673986d38e568b077c") +-Mapping("a62a76047ea24aad7639f14eb3ce0e620b77bdb7","0506789014f9aef9ffac7d7d1e22fa72c7b85ab7") +-Mapping("82cf3a4486bc882207a09bf0d9e2dea4632781aa","413ab57c0210ecbe92298c53ec4e1e39f97e4e4c") +-Mapping("1ed41b072093fe7cccd232f9a2964c5fb6ab9f60","4646a88b7a1e68326d092b9cbbbbdd616a51077f") +-Mapping("07a34df18b437319a7ff510077bbab95cf7ec6bc","df7d9f383848dcb31a2f94bb1df5270ea21aff4b") +-Mapping("3d6705aa5abffe94c83bf09af8c3ba3c599845fc","b777552167d2651ceb13437f9fde4dca95045912") +-Mapping("689fca01c5a1eac2d240bf08aa728171a28f2285","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("e83f7563495dbe2629b0cbc738afb0808c4482e1","ecef6c7c809eba2a4eed5e281f19ab7331998c6f") +-Mapping("7ceebd98c6a15ae30e772eebb676b63ffa1a8122","5d90154886039ddbd7c1b8bf4cc273b774b14ec7") +-Mapping("bbc677480db8da85ea302e1e89d3df1f00e435bf","9fe551ae49289ce6f693ca0dabf4c9c15164f67d") +-Mapping("f8d394e5184fe3af761ea1e5ba73f993cfb36dfe","fb1aa5624dff1d96249080fe365ed794431f45db") +-Mapping("25c8c53dd994acb3f4f7c02fe6bb46076393f8b0","de597fca40d129435c53a69c6662d7bfac29771d") +-Mapping("1705a7d64b833d1c4b69958b0627bd054e6d764b","ab8995bbca73be761402585ead491111163c44d6") +-Mapping("a601302ff0217b91589b5a7310a8a23adb843fdc","8d48e3bbb2da2f5eb5f4a95efd6846e9ea93a160") +-Mapping("1ce08f9d631ef767c915270bc63283c6af40dc3f","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("0b36e9dea3f2ff25b1d0df2669836c33cce89ae5","b03d3dc478ba13f405cf9a877a4894de096a1cc1") +-Mapping("6d77e45f01079fe3d40180b3e256e414ab379f63","4436c9d35498e7ae3da261f6141d6d73b915e1e8") +-Mapping("72b2abfd65ba024e12d7fe51852a309419f494d8","edb5214b29cd7de06dd10f673986d38e568b077c") +-Mapping("2b8116dced2c6c5d02e1c4359e89dc0919d6001b","b03d3dc478ba13f405cf9a877a4894de096a1cc1") +-Mapping("3f5aee2d5241139d808f4fdece0026603489afd1","410550665601a8abe8935f7b55d5732fe4c4224f") +-Mapping("29a54035c77cb2ba7ea2c24b2437760d0495a2c8","dad56c39474377c7d47e261b380d0be3aed104cc") +-Mapping("f4db9ffb22dfcb702dbdb2e0607cb91791866b57","bdaa76cfde64d06bb93c1f9102a0312d84cd0983") +-Mapping("c20d7eecbc0928b57da8fe30b2ef8528e2bdd5be","61150353bf9cc415f4554a9b4851c14e4255329f") +-Mapping("03f19f7ff128a3b01eeab3f87f04cce22883f006","b94e59cc41f8eeb36ee269cae3275d7620189c14") +-Mapping("c0b64d97beebb09325b5587abed39f4f1621026f","8a18fb0f7396ceb1ca18cd82ca3deb795f5e60b2") +-Mapping("175631311716d7dfeceec40d2587cde7142ffa8c","dd8f07223346b06da723c25a3ac42f874e6c945c") +-Mapping("9b471a3f5fe57e5c6e08acf665f2094422415a3d","250eeb4c3c00b7831226cf5266aacb5fca1e13f3") diff --git a/patches/03c64bf532ceec915f74460daf5344bb8ccf23d3.patch b/patches/03c64bf532ceec915f74460daf5344bb8ccf23d3.patch new file mode 100644 index 0000000..9e42fa1 --- /dev/null +++ b/patches/03c64bf532ceec915f74460daf5344bb8ccf23d3.patch @@ -0,0 +1,1862 @@ +diff --git a/buffered.rs b/buffered.rs +index 8862226..7898006 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -222,7 +215,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -240,7 +232,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -260,7 +251,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -298,7 +288,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -318,7 +307,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -331,7 +319,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -442,7 +429,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -477,7 +463,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -492,7 +477,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -510,7 +494,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -557,7 +540,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -577,7 +559,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -595,7 +576,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -616,7 +596,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -640,7 +619,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -649,7 +627,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -685,7 +662,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -698,7 +674,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -708,7 +683,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -747,7 +721,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -782,28 +755,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -874,7 +836,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -895,7 +856,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -916,7 +876,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -937,7 +896,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -962,7 +920,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -990,7 +947,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -998,7 +954,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1104,7 +1059,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index f36aa18..89d0701 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -268,7 +259,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -279,15 +270,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -320,6 +320,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -348,6 +349,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -360,7 +362,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -378,7 +379,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -394,7 +395,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -410,8 +411,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index 3b55d9b..c754d1f 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -432,12 +396,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -466,8 +429,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -493,10 +455,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -509,8 +470,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -518,13 +477,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -532,34 +489,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index b7f82e6..c857f83 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -25,11 +29,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -40,7 +46,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -67,14 +72,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -97,7 +101,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -114,11 +118,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -129,7 +135,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -156,14 +162,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -207,7 +213,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -265,6 +270,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -274,7 +280,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -292,7 +298,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -333,7 +338,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 88d5562..ef91b7b 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,53 +257,43 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -330,6 +320,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -357,10 +348,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -496,7 +489,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning + /// how many bytes were read. +@@ -563,7 +555,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -574,7 +565,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -601,7 +591,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -654,7 +643,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -697,7 +686,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -760,7 +749,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -814,7 +802,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -856,7 +843,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -894,7 +880,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -933,7 +918,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -942,22 +926,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -970,10 +996,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1008,7 +1033,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1032,7 +1056,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1042,7 +1065,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1055,18 +1077,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1079,10 +1097,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1116,7 +1133,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1140,7 +1156,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1151,13 +1166,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1171,21 +1184,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1239,7 +1249,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. + /// +@@ -1287,7 +1296,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1298,7 +1306,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1326,7 +1333,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1361,7 +1367,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1414,7 +1419,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1470,7 +1474,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1505,7 +1508,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1521,7 +1523,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1559,7 +1560,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1598,7 +1598,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1610,29 +1609,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1711,7 +1707,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1752,7 +1748,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1774,7 +1769,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1830,7 +1824,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1889,7 +1882,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1930,7 +1922,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -1972,7 +1963,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -1987,7 +1977,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2013,7 +2002,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2036,7 +2024,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2063,20 +2050,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2104,7 +2088,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2129,7 +2113,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2164,7 +2147,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2192,7 +2174,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2217,7 +2198,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2242,7 +2222,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2271,13 +2250,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2295,6 +2272,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2303,7 +2281,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2330,13 +2308,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2360,14 +2336,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2392,13 +2368,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b09161b..e52119e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -185,7 +179,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -217,12 +209,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -241,7 +231,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/04f0d309dcbaa8425c702d1439592b87fff0a69e.patch b/patches/04f0d309dcbaa8425c702d1439592b87fff0a69e.patch new file mode 100644 index 0000000..399271f --- /dev/null +++ b/patches/04f0d309dcbaa8425c702d1439592b87fff0a69e.patch @@ -0,0 +1,1761 @@ +diff --git a/buffered.rs b/buffered.rs +index aaf628e..259eba3 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,13 +1,13 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, Initializer, DEFAULT_BUF_SIZE, Error, ErrorKind, SeekFrom, IoSlice, + IoSliceMut}; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -47,7 +47,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -71,7 +70,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -92,7 +90,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -127,7 +124,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { &self.inner } + + /// Gets a mutable reference to the underlying reader. +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { &mut self.inner } + + /// Returns a reference to the internally buffered data. +@@ -172,7 +167,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -195,7 +189,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { self.inner } + + /// Invalidates all data in the internal buffer. +@@ -211,7 +204,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -231,7 +223,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -269,7 +260,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -289,7 +279,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader where R: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufReader") +@@ -299,7 +288,6 @@ impl fmt::Debug for BufReader where R: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -408,7 +396,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -443,7 +430,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -458,7 +444,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -476,7 +461,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { + inner: Some(inner), +@@ -525,7 +509,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.as_ref().unwrap() } + + /// Gets a mutable reference to the underlying writer. +@@ -543,7 +526,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.as_mut().unwrap() } + + /// Returns a reference to the internally buffered data. +@@ -559,7 +541,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -583,7 +564,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -592,7 +572,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -628,7 +607,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufWriter") +@@ -638,7 +616,6 @@ impl fmt::Debug for BufWriter where W: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -648,7 +625,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -687,7 +663,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { &self.1 } + + /// Returns the buffered writer instance which generated the error. +@@ -720,23 +695,13 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { self.0 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { iie.1 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -807,7 +772,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -828,7 +792,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -849,7 +812,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { + inner: BufWriter::with_capacity(capacity, inner), +@@ -873,7 +835,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.get_ref() } + + /// Gets a mutable reference to the underlying writer. +@@ -896,7 +857,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.get_mut() } + + /// Unwraps this `LineWriter`, returning the underlying writer. +@@ -922,7 +882,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { +@@ -933,7 +892,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -978,7 +936,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("LineWriter") +diff --git a/cursor.rs b/cursor.rs +index a94176e..7768d39 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Initializer, SeekFrom, Error, ErrorKind, IoSlice, IoSliceMut}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { self.inner } + + /// Gets a reference to the underlying value in this cursor. +@@ -128,7 +125,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { &self.inner } + + /// Gets a mutable reference to the underlying value in this cursor. +@@ -147,7 +143,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { &mut self.inner } + + /// Returns the current position of this cursor. +@@ -169,7 +164,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { self.pos } + + /// Sets the position of this cursor. +@@ -189,11 +183,9 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { self.pos = pos; } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor where T: AsRef<[u8]> { + fn seek(&mut self, style: SeekFrom) -> io::Result { + let (base_pos, offset) = match style { +@@ -222,10 +214,9 @@ impl io::Seek for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor where T: AsRef<[u8]> { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -244,7 +235,7 @@ impl Read for Cursor where T: AsRef<[u8]> { + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -255,12 +246,16 @@ impl Read for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor where T: AsRef<[u8]> { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++impl Cursor where T: AsRef<[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor where T: AsRef<[u8]> { ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { self.get_buf() } + fn consume(&mut self, amt: usize) { self.pos += amt as u64; } + } + +@@ -292,6 +287,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new(ErrorKind::InvalidInput, +@@ -318,6 +314,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -331,7 +328,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -347,7 +343,7 @@ impl Write for Cursor<&mut [u8]> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -361,7 +357,7 @@ impl Write for Cursor<&mut Vec> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -375,8 +371,8 @@ impl Write for Cursor> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index c29a68e..c94d8c5 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,13 @@ +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; +-use crate::convert::From; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++use core::convert::Into; ++use core::fmt; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++use core::result; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; ++use core::convert::From; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +43,6 @@ use crate::convert::From; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +56,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +69,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +90,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +130,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +142,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +156,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +186,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -245,14 +230,13 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error +- where E: Into> ++ where E: Into + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { + repr: Repr::Custom(Box::new(Custom { + kind, +@@ -261,24 +245,6 @@ impl Error { + } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -304,7 +270,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -335,7 +300,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -369,12 +333,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error+Send+Sync+'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -440,12 +403,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error+Send+Sync+'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -474,8 +436,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -501,10 +462,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -516,22 +476,18 @@ impl fmt::Debug for Repr { + match *self { + Repr::Os(code) => + fmt.debug_struct("Os") +- .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)).finish(), ++ .field("code", &code).finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), + } + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -539,33 +495,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index c959f2d..b645bc8 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,13 +1,15 @@ +-use crate::cmp; +-use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, BufRead, Error, ErrorKind, +- IoSliceMut, IoSlice}; +-use crate::fmt; +-use crate::mem; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++use core::cmp; ++use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, Error, ErrorKind, IoSliceMut, IoSlice}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::fmt; ++use core::mem; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -24,11 +26,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -39,7 +43,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -62,12 +65,11 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -86,7 +88,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -103,11 +105,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -118,7 +122,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -141,12 +145,12 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -186,7 +190,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -245,6 +248,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -254,7 +258,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(*self) } +@@ -268,7 +272,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -307,7 +310,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index a8d4d11..39da12d 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,50 +257,38 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::slice; +-use crate::str; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(feature="collections")] use collections::string::String; ++use core::str; ++#[cfg(feature="collections")] use collections::vec::Vec; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::slice; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++ ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Result, Error, ErrorKind}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, sink, Sink, empty, Empty, repeat, Repeat}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stdin, stdout, stderr, Stdin, Stdout, Stderr}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StdoutLock, StderrLock, StdinLock}; +-#[unstable(feature = "print_internals", issue = "0")] +-pub use self::stdio::{_print, _eprint}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; + + pub mod prelude; +-mod buffered; ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + mod util; +-mod stdio; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { buf: &'a mut Vec, len: usize } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { self.buf.set_len(self.len); } +@@ -325,6 +313,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where F: FnOnce(&mut Vec) -> Result + { +@@ -352,10 +341,12 @@ fn append_to_string(buf: &mut String, f: F) -> Result + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation(r: &mut R, + buf: &mut Vec, + reservation_size: usize) -> Result +@@ -484,7 +475,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -552,7 +542,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -563,7 +552,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -590,7 +578,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -643,7 +630,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -686,7 +673,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -749,7 +736,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -801,7 +787,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + + /// Transforms this `Read` instance to an [`Iterator`] over its bytes. +@@ -838,7 +823,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes where Self: Sized { + Bytes { inner: self } + } +@@ -873,7 +857,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain where Self: Sized { + Chain { first: self, second: next, done_first: false } + } +@@ -909,22 +892,52 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take where Self: Sized { + Take { inner: self, limit: limit } + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -937,14 +950,12 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -954,7 +965,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -967,11 +977,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -984,14 +992,12 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1002,13 +1008,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1022,21 +1026,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1090,7 +1091,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1139,7 +1139,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1150,7 +1149,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1178,7 +1176,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1211,7 +1208,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1263,7 +1259,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1319,7 +1314,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + } + +@@ -1349,7 +1343,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1365,7 +1358,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1403,7 +1395,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1442,7 +1433,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1454,29 +1444,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + -> Result { + let mut read = 0; +@@ -1556,7 +1543,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1597,7 +1584,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1619,7 +1605,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1675,7 +1660,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1734,7 +1718,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1775,7 +1758,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split where Self: Sized { + Split { buf: self, delim: byte } + } +@@ -1814,7 +1796,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines where Self: Sized { + Lines { buf: self } + } +@@ -1826,7 +1807,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -1852,7 +1832,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -1875,7 +1854,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -1902,13 +1880,11 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain") +@@ -1918,7 +1894,6 @@ impl fmt::Debug for Chain { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -1950,7 +1925,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -1977,7 +1952,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2012,7 +1986,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { self.limit } + + /// Sets the number of bytes that can be read before this instance will +@@ -2038,7 +2011,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2063,7 +2035,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2088,7 +2059,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2117,13 +2087,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2141,6 +2109,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + let reservation_size = cmp::min(self.limit, 32) as usize; + +@@ -2148,7 +2117,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2175,13 +2144,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2205,14 +2172,14 @@ impl Iterator for Bytes { + /// `BufRead`. Please see the documentation of `split()` for more details. + /// + /// [split]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2237,13 +2204,13 @@ impl Iterator for Split { + /// `BufRead`. Please see the documentation of `lines()` for more details. + /// + /// [lines]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 2e19edf..66294a3 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Write, Seek}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{Read, Write, BufRead, Seek}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index 1efccb5..c1d94f1 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, Read, Initializer, Write, ErrorKind, BufRead, IoSlice, IoSliceMut}; +-use crate::mem; ++use core::fmt; ++use crate::io::{self, Read, Initializer, Write, ErrorKind, IoSlice, IoSliceMut}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where R: Read, W: Write + { +@@ -74,7 +74,6 @@ pub fn copy(reader: &mut R, writer: &mut W) -> io::Result< + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { _priv: () } + + /// Constructs a new handle to an empty reader. +@@ -94,10 +93,8 @@ pub struct Empty { _priv: () } + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { Empty { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { Ok(0) } +@@ -107,7 +104,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(&[]) } +@@ -115,7 +113,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -128,7 +125,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { byte: u8 } + + /// Creates an instance of a reader that infinitely repeats one byte. +@@ -145,10 +141,8 @@ pub struct Repeat { byte: u8 } + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { Repeat { byte } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -173,7 +167,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -186,7 +179,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { _priv: () } + + /// Creates an instance of a writer which will successfully consume all data. +@@ -203,10 +195,8 @@ pub struct Sink { _priv: () } + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { Sink { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { Ok(buf.len()) } +@@ -221,7 +211,6 @@ impl Write for Sink { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/0506789014f9aef9ffac7d7d1e22fa72c7b85ab7.patch b/patches/0506789014f9aef9ffac7d7d1e22fa72c7b85ab7.patch new file mode 100644 index 0000000..535e15e --- /dev/null +++ b/patches/0506789014f9aef9ffac7d7d1e22fa72c7b85ab7.patch @@ -0,0 +1,2002 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 16c18d6..f392e3c 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,6 +1,7 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DEFAULT_BUF_SIZE}; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -42,7 +43,6 @@ use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DE + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -66,7 +66,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -87,7 +86,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -117,7 +115,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -140,7 +137,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -168,7 +164,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -191,7 +186,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -215,7 +209,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -233,7 +226,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -253,7 +245,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -295,7 +286,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -315,7 +305,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -328,7 +317,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index 3b33998..d20db36 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,7 +1,8 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -63,7 +64,6 @@ use crate::io::{ + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -85,7 +85,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -103,7 +102,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -198,7 +196,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -218,7 +215,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -236,7 +232,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -256,7 +251,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -280,7 +274,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -289,7 +282,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -386,7 +378,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -399,7 +390,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -410,7 +400,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index d0c859d..a052adf 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index 6549781..0dc7440 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,7 +119,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } +@@ -143,7 +139,6 @@ impl IntoInnerError { + /// let err = into_inner_err.into_error(); + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_error(self) -> Error { + self.1 + } +@@ -167,28 +162,17 @@ impl IntoInnerError { + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// assert_eq!(recovered_writer.buffer(), b"t be actually written"); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_parts(self) -> (Error, W) { + (self.1, self.0) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/copy.rs b/copy.rs +index b88bca2..7593702 100644 +--- a/copy.rs ++++ b/copy.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, ErrorKind, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,19 +39,12 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, + W: Write, + { +- cfg_if::cfg_if! { +- if #[cfg(any(target_os = "linux", target_os = "android"))] { +- crate::sys::kernel_copy::copy_spec(reader, writer) +- } else { +- generic_copy(reader, writer) +- } +- } ++ generic_copy(reader, writer) + } + + /// The general read-write-loop implementation of +diff --git a/cursor.rs b/cursor.rs +index bbee2cc..dc75216 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,8 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,8 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn get_ref(&self) -> &T { + &self.inner + } +@@ -152,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -176,8 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn position(&self) -> u64 { + self.pos + } +@@ -199,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -245,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -274,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -285,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -326,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -354,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -366,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -389,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -410,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -431,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 00bf8b9..5c0e7cd 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -216,7 +222,6 @@ impl BufRead for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -279,6 +284,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -288,7 +294,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -310,7 +316,6 @@ impl BufRead for &[u8] { + /// If the number of bytes to be written exceeds the size of the slice, write operations will + /// return short writes: ultimately, `Ok(0)`; in this situation, `write_all` returns an error of + /// kind `ErrorKind::WriteZero`. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -356,7 +361,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 7ad9e44..3ed4851 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -246,58 +246,48 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::copy::copy; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[unstable(feature = "internal_output_capture", issue = "none")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::set_output_capture; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + pub(crate) mod copy; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -324,6 +314,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -351,10 +342,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -488,7 +481,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -559,7 +551,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -571,7 +562,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -584,7 +574,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -608,7 +597,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -660,7 +648,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -703,7 +691,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -767,7 +755,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -821,7 +808,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -858,7 +844,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -896,7 +881,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -935,7 +919,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -944,22 +927,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -972,10 +997,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1010,7 +1034,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1034,7 +1057,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1044,7 +1066,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1057,18 +1078,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1081,10 +1098,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1118,7 +1134,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1142,7 +1157,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1153,13 +1167,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1173,21 +1185,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1241,7 +1250,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1288,7 +1296,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1301,7 +1308,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1316,7 +1322,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1344,7 +1349,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1378,7 +1382,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1440,7 +1443,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1493,7 +1495,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1549,7 +1550,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1584,7 +1584,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1598,7 +1597,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1635,7 +1633,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1673,7 +1670,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1683,29 +1679,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1781,7 +1774,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1822,7 +1815,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1844,7 +1836,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1901,7 +1892,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1964,7 +1954,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2002,7 +1991,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2039,7 +2027,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2054,7 +2041,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2080,7 +2066,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2103,7 +2088,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2130,20 +2114,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2171,7 +2152,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2196,7 +2177,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2229,7 +2209,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2257,7 +2236,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2282,7 +2260,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2307,7 +2284,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2336,13 +2312,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2360,6 +2334,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2368,7 +2343,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2395,13 +2370,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2425,14 +2398,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2457,13 +2430,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index db84545..8e88c3d 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,14 +3,14 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, Initializer, IoSlice, IoSliceMut, Read, Write}; ++use core::fmt; ++use crate::io::{self, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; + + /// A reader which is always at EOF. + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -30,13 +30,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -48,7 +45,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -58,7 +56,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -69,7 +66,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -88,13 +84,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -124,7 +117,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -135,7 +127,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -156,13 +147,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -186,7 +174,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -210,7 +197,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/05fc7faacb7c33eaad6614f62a7d560b0d2660a5.patch b/patches/05fc7faacb7c33eaad6614f62a7d560b0d2660a5.patch new file mode 100644 index 0000000..b3b7f3a --- /dev/null +++ b/patches/05fc7faacb7c33eaad6614f62a7d560b0d2660a5.patch @@ -0,0 +1,1888 @@ +diff --git a/buffered.rs b/buffered.rs +index 046b1a6..2ad53d6 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -222,7 +215,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -240,7 +232,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -260,7 +251,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -302,7 +292,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -322,7 +311,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -335,7 +323,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -446,7 +433,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -481,7 +467,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -496,7 +481,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -514,7 +498,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -561,7 +544,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -581,7 +563,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -599,7 +580,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -620,7 +600,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -644,7 +623,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -653,7 +631,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -693,7 +670,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -706,7 +682,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -716,7 +691,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -755,7 +729,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -790,28 +763,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -882,7 +844,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -903,7 +864,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -924,7 +884,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -945,7 +904,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -970,7 +928,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -998,7 +955,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -1006,7 +962,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1107,7 +1062,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index f3e3fc8..0e6fcdb 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -272,7 +263,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -283,15 +274,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -324,6 +324,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -352,6 +353,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -364,7 +366,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -387,7 +388,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -408,7 +409,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -429,8 +430,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index d80a388..8991308 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -432,12 +396,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -466,8 +429,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -493,10 +455,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -509,8 +470,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -518,13 +477,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -532,34 +489,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 01dff0b..eb78a0f 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -30,11 +34,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -45,7 +51,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -77,14 +82,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -107,7 +111,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -129,11 +133,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -144,7 +150,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -176,14 +182,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -227,7 +233,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -290,6 +295,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -299,7 +305,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -317,7 +323,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -363,7 +368,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index ebe6d09..6e5f868 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -258,54 +258,44 @@ + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + // ignore-tidy-filelength + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::mem; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++use core::mem; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -332,6 +322,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -359,10 +350,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -498,7 +491,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning + /// how many bytes were read. +@@ -570,7 +562,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -582,7 +573,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -595,7 +585,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -622,7 +611,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -675,7 +663,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -718,7 +706,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -781,7 +769,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -835,7 +822,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -877,7 +863,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -915,7 +900,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -954,7 +938,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -963,22 +946,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -991,10 +1016,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1029,7 +1053,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1053,7 +1076,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1063,7 +1085,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1076,18 +1097,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1100,10 +1117,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1137,7 +1153,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1161,7 +1176,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1172,13 +1186,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1192,21 +1204,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1260,7 +1269,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. + /// +@@ -1308,7 +1316,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1319,7 +1326,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1332,7 +1338,6 @@ pub trait Write { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1360,7 +1365,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1395,7 +1399,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1459,7 +1462,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + while !bufs.is_empty() { + match self.write_vectored(bufs) { +@@ -1512,7 +1514,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1568,7 +1569,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1603,7 +1603,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1619,7 +1618,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1657,7 +1655,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1696,7 +1693,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1708,29 +1704,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1809,7 +1802,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1850,7 +1843,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1872,7 +1864,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1928,7 +1919,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1987,7 +1977,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2028,7 +2017,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2070,7 +2058,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2085,7 +2072,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2111,7 +2097,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2134,7 +2119,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2161,20 +2145,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2202,7 +2183,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2227,7 +2208,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2262,7 +2242,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2290,7 +2269,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2315,7 +2293,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2340,7 +2317,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2369,13 +2345,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2393,6 +2367,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2401,7 +2376,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2428,13 +2403,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2458,14 +2431,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2490,13 +2463,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b9d5dc2..07d090e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -190,7 +184,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -203,7 +196,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -222,12 +214,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -251,7 +241,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/08f2904dfaf5e75fbcc1305c8b0aad5fae71a4ff.patch b/patches/08f2904dfaf5e75fbcc1305c8b0aad5fae71a4ff.patch new file mode 100644 index 0000000..9e42fa1 --- /dev/null +++ b/patches/08f2904dfaf5e75fbcc1305c8b0aad5fae71a4ff.patch @@ -0,0 +1,1862 @@ +diff --git a/buffered.rs b/buffered.rs +index 8862226..7898006 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -222,7 +215,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -240,7 +232,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -260,7 +251,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -298,7 +288,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -318,7 +307,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -331,7 +319,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -442,7 +429,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -477,7 +463,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -492,7 +477,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -510,7 +494,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -557,7 +540,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -577,7 +559,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -595,7 +576,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -616,7 +596,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -640,7 +619,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -649,7 +627,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -685,7 +662,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -698,7 +674,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -708,7 +683,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -747,7 +721,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -782,28 +755,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -874,7 +836,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -895,7 +856,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -916,7 +876,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -937,7 +896,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -962,7 +920,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -990,7 +947,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -998,7 +954,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1104,7 +1059,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index f36aa18..89d0701 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -268,7 +259,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -279,15 +270,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -320,6 +320,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -348,6 +349,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -360,7 +362,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -378,7 +379,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -394,7 +395,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -410,8 +411,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index 3b55d9b..c754d1f 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -432,12 +396,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -466,8 +429,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -493,10 +455,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -509,8 +470,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -518,13 +477,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -532,34 +489,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index b7f82e6..c857f83 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -25,11 +29,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -40,7 +46,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -67,14 +72,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -97,7 +101,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -114,11 +118,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -129,7 +135,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -156,14 +162,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -207,7 +213,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -265,6 +270,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -274,7 +280,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -292,7 +298,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -333,7 +338,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 88d5562..ef91b7b 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,53 +257,43 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -330,6 +320,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -357,10 +348,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -496,7 +489,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning + /// how many bytes were read. +@@ -563,7 +555,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -574,7 +565,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -601,7 +591,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -654,7 +643,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -697,7 +686,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -760,7 +749,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -814,7 +802,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -856,7 +843,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -894,7 +880,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -933,7 +918,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -942,22 +926,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -970,10 +996,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1008,7 +1033,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1032,7 +1056,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1042,7 +1065,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1055,18 +1077,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1079,10 +1097,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1116,7 +1133,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1140,7 +1156,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1151,13 +1166,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1171,21 +1184,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1239,7 +1249,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. + /// +@@ -1287,7 +1296,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1298,7 +1306,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1326,7 +1333,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1361,7 +1367,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1414,7 +1419,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1470,7 +1474,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1505,7 +1508,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1521,7 +1523,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1559,7 +1560,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1598,7 +1598,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1610,29 +1609,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1711,7 +1707,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1752,7 +1748,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1774,7 +1769,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1830,7 +1824,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1889,7 +1882,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1930,7 +1922,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -1972,7 +1963,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -1987,7 +1977,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2013,7 +2002,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2036,7 +2024,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2063,20 +2050,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2104,7 +2088,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2129,7 +2113,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2164,7 +2147,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2192,7 +2174,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2217,7 +2198,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2242,7 +2222,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2271,13 +2250,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2295,6 +2272,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2303,7 +2281,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2330,13 +2308,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2360,14 +2336,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2392,13 +2368,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b09161b..e52119e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -185,7 +179,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -217,12 +209,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -241,7 +231,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/0af3bd01dfae488392dc6f08daa2d0d8d370fb00.patch b/patches/0af3bd01dfae488392dc6f08daa2d0d8d370fb00.patch new file mode 100644 index 0000000..ff9fd7a --- /dev/null +++ b/patches/0af3bd01dfae488392dc6f08daa2d0d8d370fb00.patch @@ -0,0 +1,1903 @@ +diff --git a/buffered.rs b/buffered.rs +index 5ad8f81..8313e78 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -3,15 +3,15 @@ + #[cfg(test)] + mod tests; + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -52,7 +52,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -76,7 +75,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -97,7 +95,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -127,7 +124,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -150,7 +146,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -178,7 +173,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -201,7 +195,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -225,7 +218,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -243,7 +235,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -263,7 +254,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -305,7 +295,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -325,7 +314,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -338,7 +326,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -447,7 +434,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: Write::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: Write::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -482,7 +468,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -497,7 +482,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -515,7 +499,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -610,7 +593,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -630,7 +612,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -648,7 +629,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -668,7 +648,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -692,7 +671,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -701,7 +679,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -765,7 +742,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -778,7 +754,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -789,7 +764,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -829,7 +803,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -864,28 +837,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -1222,7 +1184,6 @@ impl<'a, W: Write> Write for LineWriterShim<'a, W> { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -1242,7 +1203,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -1263,7 +1223,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -1284,7 +1243,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -1309,7 +1267,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -1337,7 +1294,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner + .into_inner() +@@ -1345,7 +1301,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -1376,7 +1331,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index 5733735..0fdd84a 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,7 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -111,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -129,7 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -150,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -196,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -242,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -271,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -282,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -323,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -351,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -363,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -386,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -407,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -428,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index e09e7ba..126a710 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -230,7 +236,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -293,6 +298,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -302,7 +308,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -320,7 +326,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -366,7 +371,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index adea8a8..e647c6b 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -247,56 +247,46 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -323,6 +313,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -350,10 +341,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -487,7 +480,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -558,7 +550,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -570,7 +561,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -583,7 +573,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -607,7 +596,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -659,7 +647,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -702,7 +690,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -766,7 +754,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -820,7 +807,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -857,7 +843,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -895,7 +880,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -934,7 +918,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -943,22 +926,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -971,10 +996,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1009,7 +1033,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1033,7 +1056,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1043,7 +1065,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1056,18 +1077,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1080,10 +1097,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1117,7 +1133,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1141,7 +1156,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1152,13 +1166,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1172,21 +1184,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1240,7 +1249,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1287,7 +1295,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1300,7 +1307,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1315,7 +1321,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1343,7 +1348,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1377,7 +1381,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1439,7 +1442,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1492,7 +1494,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1548,7 +1549,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1583,7 +1583,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1597,7 +1596,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1634,7 +1632,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1672,7 +1669,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1682,29 +1678,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1780,7 +1773,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1821,7 +1814,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1843,7 +1835,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1900,7 +1891,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1963,7 +1953,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2002,7 +1991,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2039,7 +2027,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2054,7 +2041,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2080,7 +2066,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2103,7 +2088,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2130,20 +2114,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2171,7 +2152,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2196,7 +2177,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2229,7 +2209,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2257,7 +2236,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2282,7 +2260,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2307,7 +2284,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2336,13 +2312,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2360,6 +2334,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2368,7 +2343,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2395,13 +2370,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2425,14 +2398,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2457,13 +2430,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index 44d2937..a7d9389 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,9 +3,10 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -45,7 +46,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -81,7 +81,6 @@ where + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -101,12 +100,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -118,7 +115,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -128,7 +126,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -139,7 +136,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -158,12 +154,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -193,7 +187,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -204,7 +197,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -225,12 +217,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -254,7 +244,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/11ce918c75b05d065ce3bf98b20d62465b5afc55.patch b/patches/11ce918c75b05d065ce3bf98b20d62465b5afc55.patch new file mode 100644 index 0000000..adcc920 --- /dev/null +++ b/patches/11ce918c75b05d065ce3bf98b20d62465b5afc55.patch @@ -0,0 +1,1986 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 16c18d6..f392e3c 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,6 +1,7 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DEFAULT_BUF_SIZE}; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -42,7 +43,6 @@ use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DE + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -66,7 +66,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -87,7 +86,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -117,7 +115,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -140,7 +137,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -168,7 +164,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -191,7 +186,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -215,7 +209,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -233,7 +226,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -253,7 +245,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -295,7 +286,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -315,7 +305,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -328,7 +317,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index 067ed6b..47869a7 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,7 +1,8 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -63,7 +64,6 @@ use crate::io::{ + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -85,7 +85,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -103,7 +102,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -198,7 +196,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -218,7 +215,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -236,7 +232,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -256,7 +251,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -280,7 +274,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -289,7 +282,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -353,7 +345,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -366,7 +357,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -377,7 +367,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index a80d08d..20bd401 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index f9caeaf..c21de5c 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,28 +119,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/copy.rs b/copy.rs +index b88bca2..7593702 100644 +--- a/copy.rs ++++ b/copy.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, ErrorKind, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,19 +39,12 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, + W: Write, + { +- cfg_if::cfg_if! { +- if #[cfg(any(target_os = "linux", target_os = "android"))] { +- crate::sys::kernel_copy::copy_spec(reader, writer) +- } else { +- generic_copy(reader, writer) +- } +- } ++ generic_copy(reader, writer) + } + + /// The general read-write-loop implementation of +diff --git a/cursor.rs b/cursor.rs +index bbee2cc..dc75216 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,8 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,8 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn get_ref(&self) -> &T { + &self.inner + } +@@ -152,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -176,8 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn position(&self) -> u64 { + self.pos + } +@@ -199,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -245,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -274,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -285,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -326,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -354,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -366,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -389,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -410,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -431,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 6b3c86c..093d9c3 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -216,7 +222,6 @@ impl BufRead for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -279,6 +284,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -288,7 +294,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -306,7 +312,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -352,7 +357,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 703c375..2df06ce 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -247,58 +247,48 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::copy::copy; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[unstable(feature = "internal_output_capture", issue = "none")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::set_output_capture; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + pub(crate) mod copy; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -325,6 +315,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -352,10 +343,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -489,7 +482,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -560,7 +552,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -572,7 +563,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -585,7 +575,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -609,7 +598,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -661,7 +649,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -704,7 +692,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -768,7 +756,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -822,7 +809,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -859,7 +845,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -897,7 +882,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -936,7 +920,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -945,22 +928,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -973,10 +998,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1011,7 +1035,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1035,7 +1058,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1045,7 +1067,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1058,18 +1079,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1082,10 +1099,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1119,7 +1135,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1143,7 +1158,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1154,13 +1168,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1174,21 +1186,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1242,7 +1251,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1289,7 +1297,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1302,7 +1309,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1317,7 +1323,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1345,7 +1350,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1379,7 +1383,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1441,7 +1444,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1494,7 +1496,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1550,7 +1551,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1585,7 +1585,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1599,7 +1598,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1636,7 +1634,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1674,7 +1671,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1684,29 +1680,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1782,7 +1775,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1823,7 +1816,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1845,7 +1837,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1902,7 +1893,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1965,7 +1955,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2004,7 +1993,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2041,7 +2029,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2056,7 +2043,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2082,7 +2068,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2105,7 +2090,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2132,20 +2116,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2173,7 +2154,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2198,7 +2179,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2231,7 +2211,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2259,7 +2238,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2284,7 +2262,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2309,7 +2286,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2338,13 +2314,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2362,6 +2336,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2370,7 +2345,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2397,13 +2372,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2427,14 +2400,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2459,13 +2432,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index db84545..8e88c3d 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,14 +3,14 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, Initializer, IoSlice, IoSliceMut, Read, Write}; ++use core::fmt; ++use crate::io::{self, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; + + /// A reader which is always at EOF. + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -30,13 +30,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -48,7 +45,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -58,7 +56,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -69,7 +66,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -88,13 +84,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -124,7 +117,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -135,7 +127,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -156,13 +147,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -186,7 +174,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -210,7 +197,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/1b946106b7955d3dcde26719b9b62a5a2c4b78fe.patch b/patches/1b946106b7955d3dcde26719b9b62a5a2c4b78fe.patch new file mode 100644 index 0000000..9322a85 --- /dev/null +++ b/patches/1b946106b7955d3dcde26719b9b62a5a2c4b78fe.patch @@ -0,0 +1,1797 @@ +diff --git a/buffered.rs b/buffered.rs +index 9593a1b..0b6c3eb 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,13 +1,13 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, Initializer, DEFAULT_BUF_SIZE, Error, ErrorKind, SeekFrom, IoSlice, + IoSliceMut}; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -47,7 +47,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -71,7 +70,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -92,7 +90,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -127,7 +124,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { &self.inner } + + /// Gets a mutable reference to the underlying reader. +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { &mut self.inner } + + /// Returns a reference to the internally buffered data. +@@ -172,7 +167,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -195,7 +189,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { self.inner } + + /// Invalidates all data in the internal buffer. +@@ -211,7 +204,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -231,7 +223,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -269,7 +260,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -289,7 +279,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader where R: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufReader") +@@ -299,7 +288,6 @@ impl fmt::Debug for BufReader where R: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -410,7 +398,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -445,7 +432,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -460,7 +446,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -478,7 +463,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { + inner: Some(inner), +@@ -527,7 +511,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.as_ref().unwrap() } + + /// Gets a mutable reference to the underlying writer. +@@ -545,7 +528,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.as_mut().unwrap() } + + /// Returns a reference to the internally buffered data. +@@ -561,7 +543,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -585,7 +566,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -594,7 +574,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -630,7 +609,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufWriter") +@@ -640,7 +618,6 @@ impl fmt::Debug for BufWriter where W: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -650,7 +627,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -689,7 +665,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { &self.1 } + + /// Returns the buffered writer instance which generated the error. +@@ -722,23 +697,13 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { self.0 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { iie.1 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -809,7 +774,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -830,7 +794,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -851,7 +814,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { + inner: BufWriter::with_capacity(capacity, inner), +@@ -875,7 +837,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.get_ref() } + + /// Gets a mutable reference to the underlying writer. +@@ -898,7 +859,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.get_mut() } + + /// Unwraps this `LineWriter`, returning the underlying writer. +@@ -924,7 +884,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { +@@ -935,7 +894,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -980,7 +938,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("LineWriter") +diff --git a/cursor.rs b/cursor.rs +index a94176e..7768d39 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Initializer, SeekFrom, Error, ErrorKind, IoSlice, IoSliceMut}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { self.inner } + + /// Gets a reference to the underlying value in this cursor. +@@ -128,7 +125,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { &self.inner } + + /// Gets a mutable reference to the underlying value in this cursor. +@@ -147,7 +143,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { &mut self.inner } + + /// Returns the current position of this cursor. +@@ -169,7 +164,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { self.pos } + + /// Sets the position of this cursor. +@@ -189,11 +183,9 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { self.pos = pos; } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor where T: AsRef<[u8]> { + fn seek(&mut self, style: SeekFrom) -> io::Result { + let (base_pos, offset) = match style { +@@ -222,10 +214,9 @@ impl io::Seek for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor where T: AsRef<[u8]> { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -244,7 +235,7 @@ impl Read for Cursor where T: AsRef<[u8]> { + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -255,12 +246,16 @@ impl Read for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor where T: AsRef<[u8]> { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++impl Cursor where T: AsRef<[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor where T: AsRef<[u8]> { ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { self.get_buf() } + fn consume(&mut self, amt: usize) { self.pos += amt as u64; } + } + +@@ -292,6 +287,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new(ErrorKind::InvalidInput, +@@ -318,6 +314,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -331,7 +328,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -347,7 +343,7 @@ impl Write for Cursor<&mut [u8]> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -361,7 +357,7 @@ impl Write for Cursor<&mut Vec> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -375,8 +371,8 @@ impl Write for Cursor> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index c29a68e..c94d8c5 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,13 @@ +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; +-use crate::convert::From; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++use core::convert::Into; ++use core::fmt; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++use core::result; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; ++use core::convert::From; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +43,6 @@ use crate::convert::From; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +56,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +69,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +90,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +130,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +142,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +156,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +186,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -245,14 +230,13 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error +- where E: Into> ++ where E: Into + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { + repr: Repr::Custom(Box::new(Custom { + kind, +@@ -261,24 +245,6 @@ impl Error { + } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -304,7 +270,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -335,7 +300,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -369,12 +333,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error+Send+Sync+'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -440,12 +403,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error+Send+Sync+'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -474,8 +436,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -501,10 +462,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -516,22 +476,18 @@ impl fmt::Debug for Repr { + match *self { + Repr::Os(code) => + fmt.debug_struct("Os") +- .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)).finish(), ++ .field("code", &code).finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), + } + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -539,33 +495,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index c959f2d..b645bc8 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,13 +1,15 @@ +-use crate::cmp; +-use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, BufRead, Error, ErrorKind, +- IoSliceMut, IoSlice}; +-use crate::fmt; +-use crate::mem; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++use core::cmp; ++use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, Error, ErrorKind, IoSliceMut, IoSlice}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::fmt; ++use core::mem; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -24,11 +26,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -39,7 +43,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -62,12 +65,11 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -86,7 +88,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -103,11 +105,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -118,7 +122,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -141,12 +145,12 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -186,7 +190,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -245,6 +248,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -254,7 +258,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(*self) } +@@ -268,7 +272,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -307,7 +310,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 5060f36..1b1112d 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,50 +257,38 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::slice; +-use crate::str; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(feature="collections")] use collections::string::String; ++use core::str; ++#[cfg(feature="collections")] use collections::vec::Vec; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::slice; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++ ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Result, Error, ErrorKind}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, sink, Sink, empty, Empty, repeat, Repeat}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stdin, stdout, stderr, Stdin, Stdout, Stderr}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StdoutLock, StderrLock, StdinLock}; +-#[unstable(feature = "print_internals", issue = "0")] +-pub use self::stdio::{_print, _eprint}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; + + pub mod prelude; +-mod buffered; ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + mod util; +-mod stdio; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { buf: &'a mut Vec, len: usize } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { self.buf.set_len(self.len); } +@@ -325,6 +313,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where F: FnOnce(&mut Vec) -> Result + { +@@ -352,10 +341,12 @@ fn append_to_string(buf: &mut String, f: F) -> Result + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -489,7 +480,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -557,7 +547,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -568,7 +557,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -595,7 +583,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -648,7 +635,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -691,7 +678,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -754,7 +741,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -806,7 +792,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + + /// Transforms this `Read` instance to an [`Iterator`] over its bytes. +@@ -843,7 +828,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes where Self: Sized { + Bytes { inner: self } + } +@@ -878,7 +862,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain where Self: Sized { + Chain { first: self, second: next, done_first: false } + } +@@ -914,22 +897,64 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take where Self: Sized { + Take { inner: self, limit: limit } + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -942,10 +967,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -981,7 +1005,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1005,7 +1028,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1015,7 +1037,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1028,11 +1049,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1045,10 +1064,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1083,7 +1101,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(mem::replace(&mut bufs, &mut []), 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1107,7 +1124,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1118,13 +1134,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1138,21 +1152,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1206,7 +1217,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1255,7 +1265,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1266,7 +1275,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1294,7 +1302,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1327,7 +1334,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1379,7 +1385,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1435,7 +1440,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + } + +@@ -1465,7 +1469,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1481,7 +1484,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1519,7 +1521,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1558,7 +1559,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1570,29 +1570,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + -> Result { + let mut read = 0; +@@ -1672,7 +1669,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1713,7 +1710,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1735,7 +1731,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1791,7 +1786,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1850,7 +1844,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1891,7 +1884,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split where Self: Sized { + Split { buf: self, delim: byte } + } +@@ -1930,7 +1922,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines where Self: Sized { + Lines { buf: self } + } +@@ -1942,7 +1933,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -1968,7 +1958,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -1991,7 +1980,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2018,13 +2006,11 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain") +@@ -2034,7 +2020,6 @@ impl fmt::Debug for Chain { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2066,7 +2051,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2093,7 +2078,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2128,7 +2112,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { self.limit } + + /// Sets the number of bytes that can be read before this instance will +@@ -2154,7 +2137,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2179,7 +2161,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2204,7 +2185,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2233,13 +2213,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2257,6 +2235,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2265,7 +2244,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2292,13 +2271,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2322,14 +2299,14 @@ impl Iterator for Bytes { + /// `BufRead`. Please see the documentation of `split()` for more details. + /// + /// [split]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2354,13 +2331,13 @@ impl Iterator for Split { + /// `BufRead`. Please see the documentation of `lines()` for more details. + /// + /// [lines]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 2e19edf..66294a3 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Write, Seek}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{Read, Write, BufRead, Seek}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index 33cc87e..75b8032 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, Read, Initializer, Write, ErrorKind, BufRead, IoSlice, IoSliceMut}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, Read, Initializer, Write, ErrorKind, IoSlice, IoSliceMut}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where R: Read, W: Write + { +@@ -70,7 +70,6 @@ pub fn copy(reader: &mut R, writer: &mut W) -> io::Result< + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { _priv: () } + + /// Constructs a new handle to an empty reader. +@@ -90,10 +89,8 @@ pub struct Empty { _priv: () } + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { Empty { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { Ok(0) } +@@ -103,7 +100,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(&[]) } +@@ -111,7 +109,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -124,7 +121,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { byte: u8 } + + /// Creates an instance of a reader that infinitely repeats one byte. +@@ -141,10 +137,8 @@ pub struct Repeat { byte: u8 } + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { Repeat { byte } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -169,7 +163,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -182,7 +175,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { _priv: () } + + /// Creates an instance of a writer which will successfully consume all data. +@@ -199,10 +191,8 @@ pub struct Sink { _priv: () } + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { Sink { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { Ok(buf.len()) } +@@ -217,7 +207,6 @@ impl Write for Sink { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/1bf130519ca1c020623a550dc6b250eacea68e72.patch b/patches/1bf130519ca1c020623a550dc6b250eacea68e72.patch new file mode 100644 index 0000000..b4f3c3e --- /dev/null +++ b/patches/1bf130519ca1c020623a550dc6b250eacea68e72.patch @@ -0,0 +1,2068 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 987371f..d2af8b8 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,6 +1,7 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DEFAULT_BUF_SIZE}; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -42,7 +43,6 @@ use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DE + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -66,7 +66,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -87,7 +86,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -117,7 +115,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -140,7 +137,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -168,7 +164,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -191,7 +186,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -215,7 +209,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -233,7 +226,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -253,7 +245,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -309,7 +300,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -329,7 +319,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -342,7 +331,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index fa7bd0d..061c4c9 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,9 +1,9 @@ +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; +-use crate::mem; ++use core::mem; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -65,7 +65,6 @@ use crate::mem; + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -87,7 +86,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -105,7 +103,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -200,7 +197,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -220,7 +216,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -238,7 +233,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -258,7 +252,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -282,7 +275,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -313,7 +305,6 @@ impl BufWriter { + /// assert_eq!(recovered_writer.len(), 0); + /// assert_eq!(&buffered_data.unwrap(), b"ata"); + /// ``` +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_raw_parts(mut self) -> (W, Result, WriterPanicked>) { + let buf = mem::take(&mut self.buf); + let buf = if !self.panicked { Ok(buf) } else { Err(WriterPanicked { buf }) }; +@@ -321,7 +312,6 @@ impl BufWriter { + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + /// Error returned for the buffered data from `BufWriter::into_raw_parts`, when the underlying + /// writer has previously panicked. Contains the (possibly partly written) buffered data. + /// +@@ -355,7 +345,6 @@ pub struct WriterPanicked { + impl WriterPanicked { + /// Returns the perhaps-unwritten data. Some of this data may have been written by the + /// panicking call(s) to the underlying writer, so simply writing it again is not a good idea. +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_inner(self) -> Vec { + self.buf + } +@@ -364,22 +353,12 @@ impl WriterPanicked { + "BufWriter inner writer panicked, what data remains unwritten is not known"; + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] +-impl error::Error for WriterPanicked { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- Self::DESCRIPTION +- } +-} +- +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Display for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + write!(f, "{}", Self::DESCRIPTION) + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Debug for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("WriterPanicked") +@@ -388,7 +367,6 @@ impl fmt::Debug for WriterPanicked { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -485,7 +463,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -498,7 +475,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -509,7 +485,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index d0c859d..a052adf 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index 6549781..0dc7440 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,7 +119,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } +@@ -143,7 +139,6 @@ impl IntoInnerError { + /// let err = into_inner_err.into_error(); + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_error(self) -> Error { + self.1 + } +@@ -167,28 +162,17 @@ impl IntoInnerError { + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// assert_eq!(recovered_writer.buffer(), b"t be actually written"); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_parts(self) -> (Error, W) { + (self.1, self.0) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/copy.rs b/copy.rs +index b88bca2..7593702 100644 +--- a/copy.rs ++++ b/copy.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, ErrorKind, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,19 +39,12 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, + W: Write, + { +- cfg_if::cfg_if! { +- if #[cfg(any(target_os = "linux", target_os = "android"))] { +- crate::sys::kernel_copy::copy_spec(reader, writer) +- } else { +- generic_copy(reader, writer) +- } +- } ++ generic_copy(reader, writer) + } + + /// The general read-write-loop implementation of +diff --git a/cursor.rs b/cursor.rs +index bbee2cc..dc75216 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,8 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,8 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn get_ref(&self) -> &T { + &self.inner + } +@@ -152,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -176,8 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn position(&self) -> u64 { + self.pos + } +@@ -199,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -245,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -274,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -285,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -326,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -354,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -366,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -389,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -410,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -431,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 00bf8b9..5c0e7cd 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -216,7 +222,6 @@ impl BufRead for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -279,6 +284,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -288,7 +294,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -310,7 +316,6 @@ impl BufRead for &[u8] { + /// If the number of bytes to be written exceeds the size of the slice, write operations will + /// return short writes: ultimately, `Ok(0)`; in this situation, `write_all` returns an error of + /// kind `ErrorKind::WriteZero`. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -356,7 +361,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index db3b0e2..6e3a4c5 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -246,58 +246,48 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::copy::copy; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[unstable(feature = "internal_output_capture", issue = "none")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::set_output_capture; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + pub(crate) mod copy; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -324,6 +314,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -351,10 +342,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -505,7 +498,6 @@ pub(crate) fn default_read_exact(this: &mut R, mut buf: &mut [ + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -576,7 +568,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -588,7 +579,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -601,7 +591,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -625,7 +614,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -677,7 +665,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -720,7 +708,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -784,7 +772,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, buf: &mut [u8]) -> Result<()> { + default_read_exact(self, buf) + } +@@ -823,7 +810,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -860,7 +846,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -898,7 +883,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -937,7 +921,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -987,29 +970,71 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +-#[unstable(feature = "io_read_to_string", issue = "80218")] ++#[cfg(feature="collections")] + pub fn read_to_string(reader: &mut R) -> Result { + let mut buf = String::new(); + reader.read_to_string(&mut buf)?; + Ok(buf) + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1022,10 +1047,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1060,7 +1084,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1084,7 +1107,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1094,7 +1116,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1107,18 +1128,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1131,10 +1148,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1168,7 +1184,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1192,7 +1207,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1203,13 +1217,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1223,21 +1235,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1291,7 +1300,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1338,7 +1346,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1351,7 +1358,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1366,7 +1372,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1394,7 +1399,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1428,7 +1432,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1490,7 +1493,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1543,7 +1545,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1599,7 +1600,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1634,7 +1634,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1648,7 +1647,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1685,7 +1683,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_stream_len", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1722,7 +1719,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "seek_convenience", since = "1.51.0")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1732,29 +1728,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1830,7 +1823,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1871,7 +1864,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1893,7 +1885,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1950,7 +1941,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -2013,7 +2003,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2051,7 +2040,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2088,7 +2076,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2103,7 +2090,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2129,7 +2115,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2152,7 +2137,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2179,20 +2163,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2220,7 +2201,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2245,7 +2226,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2278,7 +2258,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2306,7 +2285,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2331,7 +2309,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2356,7 +2333,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2385,13 +2361,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2409,6 +2383,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2417,7 +2392,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2444,13 +2419,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2474,14 +2447,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2506,13 +2479,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index d806431..6b9791a 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index e43ce4c..e1f6fbc 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,14 +3,14 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write}; ++use core::fmt; ++use crate::io::{self, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; + + /// A reader which is always at EOF. + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -30,13 +30,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -48,7 +45,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -58,7 +56,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "empty_seek", since = "1.51.0")] + impl Seek for Empty { + fn seek(&mut self, _pos: SeekFrom) -> io::Result { + Ok(0) +@@ -73,7 +70,6 @@ impl Seek for Empty { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -84,7 +80,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -103,13 +98,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -139,7 +131,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -150,7 +141,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -171,13 +161,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -201,7 +188,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -225,7 +211,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/250eeb4c3c00b7831226cf5266aacb5fca1e13f3.patch b/patches/250eeb4c3c00b7831226cf5266aacb5fca1e13f3.patch new file mode 100644 index 0000000..8a7f0fa --- /dev/null +++ b/patches/250eeb4c3c00b7831226cf5266aacb5fca1e13f3.patch @@ -0,0 +1,2078 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 987371f..d2af8b8 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,6 +1,7 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DEFAULT_BUF_SIZE}; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -42,7 +43,6 @@ use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DE + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -66,7 +66,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -87,7 +86,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -117,7 +115,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -140,7 +137,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -168,7 +164,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -191,7 +186,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -215,7 +209,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -233,7 +226,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -253,7 +245,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -309,7 +300,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -329,7 +319,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -342,7 +331,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index 65bc2fc..46cd6b8 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,9 +1,9 @@ +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; +-use crate::mem; ++use core::mem; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -65,7 +65,6 @@ use crate::mem; + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -87,7 +86,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -105,7 +103,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -200,7 +197,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -220,7 +216,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -238,7 +233,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -270,7 +264,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -294,7 +287,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -325,7 +317,6 @@ impl BufWriter { + /// assert_eq!(recovered_writer.len(), 0); + /// assert_eq!(&buffered_data.unwrap(), b"ata"); + /// ``` +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_raw_parts(mut self) -> (W, Result, WriterPanicked>) { + let buf = mem::take(&mut self.buf); + let buf = if !self.panicked { Ok(buf) } else { Err(WriterPanicked { buf }) }; +@@ -333,7 +324,6 @@ impl BufWriter { + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + /// Error returned for the buffered data from `BufWriter::into_raw_parts`, when the underlying + /// writer has previously panicked. Contains the (possibly partly written) buffered data. + /// +@@ -367,7 +357,6 @@ pub struct WriterPanicked { + impl WriterPanicked { + /// Returns the perhaps-unwritten data. Some of this data may have been written by the + /// panicking call(s) to the underlying writer, so simply writing it again is not a good idea. +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_inner(self) -> Vec { + self.buf + } +@@ -376,22 +365,12 @@ impl WriterPanicked { + "BufWriter inner writer panicked, what data remains unwritten is not known"; + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] +-impl error::Error for WriterPanicked { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- Self::DESCRIPTION +- } +-} +- +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Display for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + write!(f, "{}", Self::DESCRIPTION) + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Debug for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("WriterPanicked") +@@ -400,7 +379,6 @@ impl fmt::Debug for WriterPanicked { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -497,7 +475,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -510,7 +487,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -521,7 +497,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index d0c859d..a052adf 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index 6549781..0dc7440 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,7 +119,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } +@@ -143,7 +139,6 @@ impl IntoInnerError { + /// let err = into_inner_err.into_error(); + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_error(self) -> Error { + self.1 + } +@@ -167,28 +162,17 @@ impl IntoInnerError { + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// assert_eq!(recovered_writer.buffer(), b"t be actually written"); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_parts(self) -> (Error, W) { + (self.1, self.0) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/copy.rs b/copy.rs +index 3780f20..9c52ecc 100644 +--- a/copy.rs ++++ b/copy.rs +@@ -1,5 +1,6 @@ +-use super::{BufWriter, ErrorKind, Read, Result, Write, DEFAULT_BUF_SIZE}; +-use crate::mem::MaybeUninit; ++use super::{ErrorKind, Read, Result, Write, DEFAULT_BUF_SIZE}; ++#[cfg(feature = "collections")] use super::BufWriter; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,19 +40,12 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> Result + where + R: Read, + W: Write, + { +- cfg_if::cfg_if! { +- if #[cfg(any(target_os = "linux", target_os = "android"))] { +- crate::sys::kernel_copy::copy_spec(reader, writer) +- } else { +- generic_copy(reader, writer) +- } +- } ++ generic_copy(reader, writer) + } + + /// The userspace read-write-loop implementation of `io::copy` that is used when +@@ -76,6 +70,7 @@ impl BufferedCopySpec for W { + } + } + ++#[cfg(feature = "collections")] + impl BufferedCopySpec for BufWriter { + fn copy_to(reader: &mut R, writer: &mut Self) -> Result { + if writer.capacity() < DEFAULT_BUF_SIZE { +diff --git a/cursor.rs b/cursor.rs +index bbee2cc..dc75216 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,8 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,8 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn get_ref(&self) -> &T { + &self.inner + } +@@ -152,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -176,8 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn position(&self) -> u64 { + self.pos + } +@@ -199,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -245,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -274,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -285,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -326,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -354,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -366,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -389,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -410,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -431,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 00bf8b9..5c0e7cd 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -216,7 +222,6 @@ impl BufRead for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -279,6 +284,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -288,7 +294,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -310,7 +316,6 @@ impl BufRead for &[u8] { + /// If the number of bytes to be written exceeds the size of the slice, write operations will + /// return short writes: ultimately, `Ok(0)`; in this situation, `write_all` returns an error of + /// kind `ErrorKind::WriteZero`. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -356,7 +361,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index db3b0e2..6e3a4c5 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -246,58 +246,48 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::copy::copy; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[unstable(feature = "internal_output_capture", issue = "none")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::set_output_capture; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + pub(crate) mod copy; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -324,6 +314,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -351,10 +342,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -505,7 +498,6 @@ pub(crate) fn default_read_exact(this: &mut R, mut buf: &mut [ + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -576,7 +568,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -588,7 +579,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -601,7 +591,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -625,7 +614,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -677,7 +665,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -720,7 +708,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -784,7 +772,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, buf: &mut [u8]) -> Result<()> { + default_read_exact(self, buf) + } +@@ -823,7 +810,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -860,7 +846,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -898,7 +883,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -937,7 +921,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -987,29 +970,71 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +-#[unstable(feature = "io_read_to_string", issue = "80218")] ++#[cfg(feature="collections")] + pub fn read_to_string(reader: &mut R) -> Result { + let mut buf = String::new(); + reader.read_to_string(&mut buf)?; + Ok(buf) + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1022,10 +1047,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1060,7 +1084,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1084,7 +1107,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1094,7 +1116,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1107,18 +1128,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1131,10 +1148,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1168,7 +1184,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1192,7 +1207,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1203,13 +1217,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1223,21 +1235,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1291,7 +1300,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1338,7 +1346,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1351,7 +1358,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1366,7 +1372,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1394,7 +1399,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1428,7 +1432,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1490,7 +1493,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1543,7 +1545,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1599,7 +1600,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1634,7 +1634,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1648,7 +1647,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1685,7 +1683,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_stream_len", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1722,7 +1719,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "seek_convenience", since = "1.51.0")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1732,29 +1728,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1830,7 +1823,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1871,7 +1864,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1893,7 +1885,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1950,7 +1941,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -2013,7 +2003,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2051,7 +2040,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2088,7 +2076,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2103,7 +2090,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2129,7 +2115,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2152,7 +2137,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2179,20 +2163,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2220,7 +2201,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2245,7 +2226,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2278,7 +2258,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2306,7 +2285,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2331,7 +2309,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2356,7 +2333,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2385,13 +2361,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2409,6 +2383,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2417,7 +2392,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2444,13 +2419,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2474,14 +2447,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2506,13 +2479,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index d806431..6b9791a 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index e43ce4c..e1f6fbc 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,14 +3,14 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write}; ++use core::fmt; ++use crate::io::{self, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; + + /// A reader which is always at EOF. + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -30,13 +30,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -48,7 +45,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -58,7 +56,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "empty_seek", since = "1.51.0")] + impl Seek for Empty { + fn seek(&mut self, _pos: SeekFrom) -> io::Result { + Ok(0) +@@ -73,7 +70,6 @@ impl Seek for Empty { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -84,7 +80,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -103,13 +98,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -139,7 +131,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -150,7 +141,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -171,13 +161,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -201,7 +188,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -225,7 +211,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/260514da942f281bc2dc3b14b629d3e660b3484f.patch b/patches/260514da942f281bc2dc3b14b629d3e660b3484f.patch new file mode 100644 index 0000000..c350194 --- /dev/null +++ b/patches/260514da942f281bc2dc3b14b629d3e660b3484f.patch @@ -0,0 +1,1830 @@ +diff --git a/buffered.rs b/buffered.rs +index 3ba80e7..de9bc11 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -216,7 +209,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -236,7 +228,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -274,7 +265,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -294,7 +284,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -307,7 +296,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -418,7 +406,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -453,7 +440,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -468,7 +454,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -486,7 +471,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -533,7 +517,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -553,7 +536,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -571,7 +553,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -595,7 +576,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -604,7 +584,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -640,7 +619,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -653,7 +631,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -663,7 +640,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -702,7 +678,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -737,27 +712,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -828,7 +793,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -849,7 +813,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -870,7 +833,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -891,7 +853,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -916,7 +877,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -944,7 +904,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -952,7 +911,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1058,7 +1016,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index 9787cbb..1cf83d3 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -268,7 +259,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -279,15 +270,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -320,6 +320,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -348,6 +349,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -360,7 +362,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -378,7 +379,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -394,7 +395,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -410,8 +411,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index c20bd30..99af4d1 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -434,12 +398,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -468,8 +431,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -495,10 +457,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -511,8 +472,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -520,13 +479,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -534,33 +491,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index b7f82e6..c857f83 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -25,11 +29,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -40,7 +46,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -67,14 +72,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -97,7 +101,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -114,11 +118,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -129,7 +135,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -156,14 +162,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -207,7 +213,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -265,6 +270,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -274,7 +280,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -292,7 +298,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -333,7 +338,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 95c8934..b29907e 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,53 +257,43 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -330,6 +320,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -357,10 +348,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -496,7 +489,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -564,7 +556,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -575,7 +566,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -602,7 +592,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -655,7 +644,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -698,7 +687,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -761,7 +750,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -815,7 +803,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -857,7 +844,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -895,7 +881,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -934,7 +919,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -943,16 +927,59 @@ pub trait Read { + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -965,10 +992,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1003,7 +1029,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1027,7 +1052,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1037,7 +1061,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1050,11 +1073,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1067,10 +1088,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1104,7 +1124,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1128,7 +1147,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1139,13 +1157,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1159,21 +1175,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1227,7 +1240,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1276,7 +1288,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1287,7 +1298,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1315,7 +1325,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1348,7 +1357,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1401,7 +1409,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1457,7 +1464,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1492,7 +1498,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1508,7 +1513,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1546,7 +1550,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1585,7 +1588,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1597,29 +1599,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1698,7 +1697,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1739,7 +1738,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1761,7 +1759,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1817,7 +1814,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1876,7 +1872,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1917,7 +1912,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -1959,7 +1953,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -1974,7 +1967,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2000,7 +1992,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2023,7 +2014,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2050,20 +2040,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2091,7 +2078,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2116,7 +2103,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2151,7 +2137,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2179,7 +2164,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2204,7 +2188,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2229,7 +2212,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2258,13 +2240,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2282,6 +2262,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2290,7 +2271,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2317,13 +2298,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2347,14 +2326,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2379,13 +2358,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b09161b..e52119e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -185,7 +179,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -217,12 +209,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -241,7 +231,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/276b54e9c930c4ff015e1958ad1c640deffd29b2.patch b/patches/276b54e9c930c4ff015e1958ad1c640deffd29b2.patch new file mode 100644 index 0000000..5908559 --- /dev/null +++ b/patches/276b54e9c930c4ff015e1958ad1c640deffd29b2.patch @@ -0,0 +1,1850 @@ +diff --git a/buffered.rs b/buffered.rs +index 8862226..7898006 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -222,7 +215,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -240,7 +232,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -260,7 +251,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -298,7 +288,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -318,7 +307,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -331,7 +319,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -442,7 +429,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -477,7 +463,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -492,7 +477,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -510,7 +494,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -557,7 +540,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -577,7 +559,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -595,7 +576,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -616,7 +596,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -640,7 +619,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -649,7 +627,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -685,7 +662,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -698,7 +674,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -708,7 +683,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -747,7 +721,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -782,28 +755,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -874,7 +836,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -895,7 +856,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -916,7 +876,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -937,7 +896,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -962,7 +920,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -990,7 +947,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -998,7 +954,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1104,7 +1059,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index f36aa18..89d0701 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -268,7 +259,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -279,15 +270,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -320,6 +320,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -348,6 +349,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -360,7 +362,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -378,7 +379,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -394,7 +395,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -410,8 +411,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index 3b55d9b..c754d1f 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -432,12 +396,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -466,8 +429,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -493,10 +455,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -509,8 +470,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -518,13 +477,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -532,34 +489,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index b7f82e6..c857f83 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -25,11 +29,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -40,7 +46,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -67,14 +72,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -97,7 +101,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -114,11 +118,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -129,7 +135,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -156,14 +162,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -207,7 +213,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -265,6 +270,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -274,7 +280,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -292,7 +298,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -333,7 +338,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index dc83143..fc8896f 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,53 +257,43 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -330,6 +320,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -357,10 +348,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -496,7 +489,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning + /// how many bytes were read. +@@ -563,7 +555,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -574,7 +565,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -601,7 +591,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -654,7 +643,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -697,7 +686,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -760,7 +749,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -814,7 +802,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -856,7 +843,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -894,7 +880,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -933,7 +918,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -942,16 +926,60 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -964,10 +992,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1002,7 +1029,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1026,7 +1052,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1036,7 +1061,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1049,12 +1073,10 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1067,10 +1089,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1104,7 +1125,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1128,7 +1148,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1139,13 +1158,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1159,21 +1176,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1227,7 +1241,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. + /// +@@ -1275,7 +1288,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1286,7 +1298,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1314,7 +1325,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1349,7 +1359,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1402,7 +1411,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1458,7 +1466,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1493,7 +1500,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1509,7 +1515,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1547,7 +1552,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1586,7 +1590,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1598,29 +1601,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1699,7 +1699,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1740,7 +1740,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1762,7 +1761,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1818,7 +1816,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1877,7 +1874,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1918,7 +1914,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -1960,7 +1955,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -1975,7 +1969,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2001,7 +1994,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2024,7 +2016,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2051,20 +2042,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2092,7 +2080,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2117,7 +2105,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2152,7 +2139,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2180,7 +2166,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2205,7 +2190,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2230,7 +2214,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2259,13 +2242,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2283,6 +2264,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2291,7 +2273,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2318,13 +2300,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2348,14 +2328,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2380,13 +2360,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b09161b..e52119e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -185,7 +179,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -217,12 +209,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -241,7 +231,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/2c31b45ae878b821975c4ebd94cc1e49f6073fd0.patch b/patches/2c31b45ae878b821975c4ebd94cc1e49f6073fd0.patch new file mode 100644 index 0000000..cfc1572 --- /dev/null +++ b/patches/2c31b45ae878b821975c4ebd94cc1e49f6073fd0.patch @@ -0,0 +1,1891 @@ +diff --git a/buffered.rs b/buffered.rs +index b4c91cc..3c3cad2 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -197,7 +191,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -221,7 +214,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -239,7 +231,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -259,7 +250,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -301,7 +291,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -321,7 +310,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -334,7 +322,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -445,7 +432,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -480,7 +466,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -495,7 +480,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -513,7 +497,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -560,7 +543,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -580,7 +562,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -598,7 +579,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -618,7 +598,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -642,7 +621,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -651,7 +629,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -691,7 +668,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -704,7 +680,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -714,7 +689,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -753,7 +727,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -788,28 +761,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -880,7 +842,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -901,7 +862,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -922,7 +882,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -943,7 +902,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -968,7 +926,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -996,7 +953,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -1004,7 +960,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1105,7 +1060,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index f4db5f8..4f20b8a 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -272,7 +263,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -283,15 +274,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -324,6 +324,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -352,6 +353,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -364,7 +366,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -387,7 +388,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -408,7 +409,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -429,8 +430,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index f7248e7..f7311ad 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,12 +143,10 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -165,7 +154,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -174,7 +162,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -205,7 +192,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -248,36 +234,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -303,7 +270,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -334,7 +300,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -368,12 +333,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -437,12 +401,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -471,8 +434,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -498,10 +460,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -514,8 +475,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -523,13 +482,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -537,34 +494,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 01dff0b..eb78a0f 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -30,11 +34,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -45,7 +51,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -77,14 +82,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -107,7 +111,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -129,11 +133,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -144,7 +150,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -176,14 +182,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -227,7 +233,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -290,6 +295,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -299,7 +305,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -317,7 +323,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -363,7 +368,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 9eb54c2..15e51d3 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -247,53 +247,43 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -320,6 +310,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -347,10 +338,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -484,7 +477,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -555,7 +547,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -567,7 +558,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -580,7 +570,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -604,7 +593,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -656,7 +644,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -699,7 +687,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -763,7 +751,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -817,7 +804,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -855,7 +841,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -893,7 +878,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -932,7 +916,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -941,22 +924,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -969,10 +994,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1007,7 +1031,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1031,7 +1054,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1041,7 +1063,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1054,18 +1075,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1078,10 +1095,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1115,7 +1131,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1139,7 +1154,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1150,13 +1164,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1170,21 +1182,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1238,7 +1247,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Self::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1283,7 +1291,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1294,7 +1301,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1307,7 +1313,6 @@ pub trait Write { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1335,7 +1340,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1369,7 +1373,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1432,7 +1435,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1485,7 +1487,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1541,7 +1542,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1576,7 +1576,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1592,7 +1591,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1630,7 +1628,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1669,7 +1666,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1681,29 +1677,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1782,7 +1775,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1823,7 +1816,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1845,7 +1837,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: Self::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1905,7 +1896,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1968,7 +1958,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2009,7 +1998,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2048,7 +2036,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2063,7 +2050,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2089,7 +2075,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2112,7 +2097,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2139,20 +2123,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2180,7 +2161,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2205,7 +2186,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2238,7 +2218,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2266,7 +2245,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2291,7 +2269,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2316,7 +2293,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2345,13 +2321,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2369,6 +2343,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2377,7 +2352,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2404,13 +2379,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2434,14 +2407,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2466,13 +2439,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b9d5dc2..07d090e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -190,7 +184,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -203,7 +196,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -222,12 +214,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -251,7 +241,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/2c56ea38b045624dc8b42ec948fc169eaff1206a.patch b/patches/2c56ea38b045624dc8b42ec948fc169eaff1206a.patch new file mode 100644 index 0000000..972ad09 --- /dev/null +++ b/patches/2c56ea38b045624dc8b42ec948fc169eaff1206a.patch @@ -0,0 +1,2002 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 16c18d6..f392e3c 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,6 +1,7 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DEFAULT_BUF_SIZE}; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -42,7 +43,6 @@ use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DE + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -66,7 +66,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -87,7 +86,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -117,7 +115,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -140,7 +137,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -168,7 +164,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -191,7 +186,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -215,7 +209,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -233,7 +226,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -253,7 +245,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -295,7 +286,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -315,7 +305,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -328,7 +317,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index 3b33998..d20db36 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,7 +1,8 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -63,7 +64,6 @@ use crate::io::{ + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -85,7 +85,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -103,7 +102,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -198,7 +196,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -218,7 +215,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -236,7 +232,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -256,7 +251,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -280,7 +274,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -289,7 +282,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -386,7 +378,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -399,7 +390,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -410,7 +400,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index d0c859d..a052adf 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index 6549781..0dc7440 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,7 +119,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } +@@ -143,7 +139,6 @@ impl IntoInnerError { + /// let err = into_inner_err.into_error(); + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_error(self) -> Error { + self.1 + } +@@ -167,28 +162,17 @@ impl IntoInnerError { + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// assert_eq!(recovered_writer.buffer(), b"t be actually written"); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_parts(self) -> (Error, W) { + (self.1, self.0) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/copy.rs b/copy.rs +index b88bca2..7593702 100644 +--- a/copy.rs ++++ b/copy.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, ErrorKind, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,19 +39,12 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, + W: Write, + { +- cfg_if::cfg_if! { +- if #[cfg(any(target_os = "linux", target_os = "android"))] { +- crate::sys::kernel_copy::copy_spec(reader, writer) +- } else { +- generic_copy(reader, writer) +- } +- } ++ generic_copy(reader, writer) + } + + /// The general read-write-loop implementation of +diff --git a/cursor.rs b/cursor.rs +index bbee2cc..dc75216 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,8 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,8 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn get_ref(&self) -> &T { + &self.inner + } +@@ -152,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -176,8 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn position(&self) -> u64 { + self.pos + } +@@ -199,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -245,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -274,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -285,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -326,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -354,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -366,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -389,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -410,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -431,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 00bf8b9..5c0e7cd 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -216,7 +222,6 @@ impl BufRead for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -279,6 +284,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -288,7 +294,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -310,7 +316,6 @@ impl BufRead for &[u8] { + /// If the number of bytes to be written exceeds the size of the slice, write operations will + /// return short writes: ultimately, `Ok(0)`; in this situation, `write_all` returns an error of + /// kind `ErrorKind::WriteZero`. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -356,7 +361,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index dfbf6c3..7437b18 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -247,58 +247,48 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::copy::copy; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[unstable(feature = "internal_output_capture", issue = "none")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::set_output_capture; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + pub(crate) mod copy; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -325,6 +315,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -352,10 +343,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -489,7 +482,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -560,7 +552,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -572,7 +563,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -585,7 +575,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -609,7 +598,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -661,7 +649,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -704,7 +692,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -768,7 +756,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -822,7 +809,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -859,7 +845,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -897,7 +882,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -936,7 +920,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -945,22 +928,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -973,10 +998,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1011,7 +1035,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1035,7 +1058,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1045,7 +1067,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1058,18 +1079,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1082,10 +1099,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1119,7 +1135,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1143,7 +1158,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1154,13 +1168,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1174,21 +1186,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1242,7 +1251,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1289,7 +1297,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1302,7 +1309,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1317,7 +1323,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1345,7 +1350,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1379,7 +1383,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1441,7 +1444,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1494,7 +1496,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1550,7 +1551,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1585,7 +1585,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1599,7 +1598,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1636,7 +1634,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1674,7 +1671,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1684,29 +1680,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1782,7 +1775,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1823,7 +1816,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1845,7 +1837,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1902,7 +1893,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1965,7 +1955,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2004,7 +1993,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2041,7 +2029,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2056,7 +2043,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2082,7 +2068,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2105,7 +2090,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2132,20 +2116,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2173,7 +2154,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2198,7 +2179,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2231,7 +2211,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2259,7 +2238,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2284,7 +2262,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2309,7 +2286,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2338,13 +2314,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2362,6 +2336,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2370,7 +2345,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2397,13 +2372,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2427,14 +2400,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2459,13 +2432,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index db84545..8e88c3d 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,14 +3,14 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, Initializer, IoSlice, IoSliceMut, Read, Write}; ++use core::fmt; ++use crate::io::{self, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; + + /// A reader which is always at EOF. + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -30,13 +30,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -48,7 +45,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -58,7 +56,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -69,7 +66,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -88,13 +84,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -124,7 +117,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -135,7 +127,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -156,13 +147,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -186,7 +174,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -210,7 +197,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/2fee28e7138d8753487ed8895ce0f5f2e643ffad.patch b/patches/2fee28e7138d8753487ed8895ce0f5f2e643ffad.patch new file mode 100644 index 0000000..d75073f --- /dev/null +++ b/patches/2fee28e7138d8753487ed8895ce0f5f2e643ffad.patch @@ -0,0 +1,1817 @@ +diff --git a/buffered.rs b/buffered.rs +index df259dc..3cb42f9 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -216,7 +209,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -236,7 +228,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -274,7 +265,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -294,7 +284,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -307,7 +296,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -418,7 +406,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -453,7 +440,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -468,7 +454,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -486,7 +471,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -533,7 +517,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -553,7 +536,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -571,7 +553,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -595,7 +576,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -604,7 +584,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -640,7 +619,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -653,7 +631,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -663,7 +640,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -702,7 +678,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -737,27 +712,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -828,7 +793,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -849,7 +813,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -870,7 +833,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -891,7 +853,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -916,7 +877,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -944,7 +904,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -952,7 +911,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1058,7 +1016,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index a94176e..7768d39 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Initializer, SeekFrom, Error, ErrorKind, IoSlice, IoSliceMut}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { self.inner } + + /// Gets a reference to the underlying value in this cursor. +@@ -128,7 +125,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { &self.inner } + + /// Gets a mutable reference to the underlying value in this cursor. +@@ -147,7 +143,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { &mut self.inner } + + /// Returns the current position of this cursor. +@@ -169,7 +164,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { self.pos } + + /// Sets the position of this cursor. +@@ -189,11 +183,9 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { self.pos = pos; } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor where T: AsRef<[u8]> { + fn seek(&mut self, style: SeekFrom) -> io::Result { + let (base_pos, offset) = match style { +@@ -222,10 +214,9 @@ impl io::Seek for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor where T: AsRef<[u8]> { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -244,7 +235,7 @@ impl Read for Cursor where T: AsRef<[u8]> { + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -255,12 +246,16 @@ impl Read for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor where T: AsRef<[u8]> { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++impl Cursor where T: AsRef<[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor where T: AsRef<[u8]> { ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { self.get_buf() } + fn consume(&mut self, amt: usize) { self.pos += amt as u64; } + } + +@@ -292,6 +287,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new(ErrorKind::InvalidInput, +@@ -318,6 +314,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -331,7 +328,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -347,7 +343,7 @@ impl Write for Cursor<&mut [u8]> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -361,7 +357,7 @@ impl Write for Cursor<&mut Vec> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -375,8 +371,8 @@ impl Write for Cursor> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index c20bd30..99af4d1 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -434,12 +398,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -468,8 +431,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -495,10 +457,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -511,8 +472,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -520,13 +479,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -534,33 +491,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index b7f82e6..c857f83 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -25,11 +29,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -40,7 +46,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -67,14 +72,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -97,7 +101,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -114,11 +118,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -129,7 +135,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -156,14 +162,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -207,7 +213,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -265,6 +270,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -274,7 +280,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -292,7 +298,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -333,7 +338,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index a1a33ba..04bc734 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,53 +257,43 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "0")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -330,6 +320,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -357,10 +348,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -496,7 +489,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -564,7 +556,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -575,7 +566,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -602,7 +592,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -655,7 +644,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -698,7 +687,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -761,7 +750,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -815,7 +803,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -857,7 +844,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -895,7 +881,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -934,7 +919,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -943,16 +927,59 @@ pub trait Read { + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -965,10 +992,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1003,7 +1029,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1027,7 +1052,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1037,7 +1061,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1050,11 +1073,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1067,10 +1088,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1104,7 +1124,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1128,7 +1147,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1139,13 +1157,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1159,21 +1175,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1227,7 +1240,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1276,7 +1288,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1287,7 +1298,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1315,7 +1325,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1348,7 +1357,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1401,7 +1409,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1457,7 +1464,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1492,7 +1498,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1508,7 +1513,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1546,7 +1550,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1585,7 +1588,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1597,29 +1599,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1698,7 +1697,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1739,7 +1738,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1761,7 +1759,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1817,7 +1814,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1876,7 +1872,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1917,7 +1912,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -1959,7 +1953,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -1974,7 +1967,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2000,7 +1992,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2023,7 +2014,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2050,20 +2040,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2091,7 +2078,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2116,7 +2103,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2151,7 +2137,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2179,7 +2164,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2204,7 +2188,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2229,7 +2212,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2258,13 +2240,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2282,6 +2262,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2290,7 +2271,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2317,13 +2298,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2347,14 +2326,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2379,13 +2358,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b09161b..e52119e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -185,7 +179,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -217,12 +209,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -241,7 +231,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/30e49a9ead550551e879af64ba91a0316da1c422.patch b/patches/30e49a9ead550551e879af64ba91a0316da1c422.patch new file mode 100644 index 0000000..aa86902 --- /dev/null +++ b/patches/30e49a9ead550551e879af64ba91a0316da1c422.patch @@ -0,0 +1,1987 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 16c18d6..f392e3c 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,6 +1,7 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DEFAULT_BUF_SIZE}; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -42,7 +43,6 @@ use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DE + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -66,7 +66,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -87,7 +86,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -117,7 +115,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -140,7 +137,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -168,7 +164,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -191,7 +186,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -215,7 +209,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -233,7 +226,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -253,7 +245,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -295,7 +286,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -315,7 +305,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -328,7 +317,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index 067ed6b..47869a7 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,7 +1,8 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -63,7 +64,6 @@ use crate::io::{ + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -85,7 +85,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -103,7 +102,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -198,7 +196,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -218,7 +215,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -236,7 +232,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -256,7 +251,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -280,7 +274,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -289,7 +282,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -353,7 +345,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -366,7 +357,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -377,7 +367,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index a80d08d..20bd401 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index f9caeaf..c21de5c 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,28 +119,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/copy.rs b/copy.rs +index b88bca2..7593702 100644 +--- a/copy.rs ++++ b/copy.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, ErrorKind, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,19 +39,12 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, + W: Write, + { +- cfg_if::cfg_if! { +- if #[cfg(any(target_os = "linux", target_os = "android"))] { +- crate::sys::kernel_copy::copy_spec(reader, writer) +- } else { +- generic_copy(reader, writer) +- } +- } ++ generic_copy(reader, writer) + } + + /// The general read-write-loop implementation of +diff --git a/cursor.rs b/cursor.rs +index bbee2cc..dc75216 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,8 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,8 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn get_ref(&self) -> &T { + &self.inner + } +@@ -152,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -176,8 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn position(&self) -> u64 { + self.pos + } +@@ -199,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -245,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -274,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -285,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -326,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -354,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -366,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -389,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -410,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -431,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 6642610..efbe402 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -230,7 +236,6 @@ impl Write for dyn ::realstd::io::LocalOutput { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -293,6 +298,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -302,7 +308,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -320,7 +326,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -366,7 +371,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 57413f9..2df06ce 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -247,60 +247,48 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::copy::copy; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print, LocalOutput}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{empty, repeat, sink, Empty, Repeat, Sink}; + +-pub(crate) use self::stdio::clone_io; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + +-mod buffered; ++#[cfg(feature="collections")] mod buffered; + pub(crate) mod copy; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -327,6 +315,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -354,10 +343,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -491,7 +482,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -562,7 +552,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -574,7 +563,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -587,7 +575,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -611,7 +598,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -663,7 +649,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -706,7 +692,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -770,7 +756,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -824,7 +809,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -861,7 +845,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -899,7 +882,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -938,7 +920,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -947,22 +928,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -975,10 +998,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1013,7 +1035,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1037,7 +1058,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1047,7 +1067,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1060,18 +1079,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1084,10 +1099,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1121,7 +1135,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1145,7 +1158,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1156,13 +1168,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1176,21 +1186,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1244,7 +1251,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1291,7 +1297,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1304,7 +1309,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1319,7 +1323,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1347,7 +1350,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1381,7 +1383,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1443,7 +1444,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1496,7 +1496,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1552,7 +1551,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1587,7 +1585,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1601,7 +1598,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1638,7 +1634,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1676,7 +1671,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1686,29 +1680,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1784,7 +1775,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1825,7 +1816,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1847,7 +1837,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1904,7 +1893,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1967,7 +1955,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2006,7 +1993,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2043,7 +2029,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2058,7 +2043,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2084,7 +2068,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2107,7 +2090,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2134,20 +2116,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2175,7 +2154,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2200,7 +2179,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2233,7 +2211,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2261,7 +2238,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2286,7 +2262,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2311,7 +2286,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2340,13 +2314,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2364,6 +2336,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2372,7 +2345,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2399,13 +2372,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2429,14 +2400,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2461,13 +2432,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index db84545..8e88c3d 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,14 +3,14 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, Initializer, IoSlice, IoSliceMut, Read, Write}; ++use core::fmt; ++use crate::io::{self, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; + + /// A reader which is always at EOF. + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -30,13 +30,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -48,7 +45,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -58,7 +56,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -69,7 +66,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -88,13 +84,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -124,7 +117,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -135,7 +127,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -156,13 +147,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -186,7 +174,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -210,7 +197,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/353df59893f4dc249f06047dca659b5b2172063f.patch b/patches/353df59893f4dc249f06047dca659b5b2172063f.patch new file mode 100644 index 0000000..3499f86 --- /dev/null +++ b/patches/353df59893f4dc249f06047dca659b5b2172063f.patch @@ -0,0 +1,1893 @@ +diff --git a/buffered.rs b/buffered.rs +index b4c91cc..3c3cad2 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -197,7 +191,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -221,7 +214,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -239,7 +231,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -259,7 +250,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -301,7 +291,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -321,7 +310,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -334,7 +322,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -445,7 +432,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -480,7 +466,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -495,7 +480,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -513,7 +497,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -560,7 +543,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -580,7 +562,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -598,7 +579,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -618,7 +598,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -642,7 +621,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -651,7 +629,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -691,7 +668,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -704,7 +680,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -714,7 +689,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -753,7 +727,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -788,28 +761,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -880,7 +842,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -901,7 +862,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -922,7 +882,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -943,7 +902,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -968,7 +926,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -996,7 +953,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -1004,7 +960,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1105,7 +1060,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index f4db5f8..4f20b8a 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -272,7 +263,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -283,15 +274,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -324,6 +324,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -352,6 +353,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -364,7 +366,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -387,7 +388,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -408,7 +409,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -429,8 +430,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index f7248e7..f7311ad 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,12 +143,10 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -165,7 +154,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -174,7 +162,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -205,7 +192,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -248,36 +234,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -303,7 +270,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -334,7 +300,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -368,12 +333,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -437,12 +401,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -471,8 +434,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -498,10 +460,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -514,8 +475,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -523,13 +482,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -537,34 +494,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 01dff0b..eb78a0f 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -30,11 +34,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -45,7 +51,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -77,14 +82,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -107,7 +111,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -129,11 +133,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -144,7 +150,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -176,14 +182,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -227,7 +233,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -290,6 +295,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -299,7 +305,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -317,7 +323,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -363,7 +368,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 717d286..8a46366 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -258,54 +258,44 @@ + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + // ignore-tidy-filelength + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::mem; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++use core::mem; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -332,6 +322,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -359,10 +350,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -498,7 +491,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning + /// how many bytes were read. +@@ -570,7 +562,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -582,7 +573,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -595,7 +585,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -622,7 +611,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -675,7 +663,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -718,7 +706,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -781,7 +769,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -835,7 +822,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -877,7 +863,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -915,7 +900,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -954,7 +938,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -963,22 +946,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -991,10 +1016,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1029,7 +1053,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1053,7 +1076,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1063,7 +1085,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1076,18 +1097,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1100,10 +1117,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1137,7 +1153,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1161,7 +1176,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1172,13 +1186,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1192,21 +1204,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1260,7 +1269,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. + /// +@@ -1308,7 +1316,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1319,7 +1326,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1332,7 +1338,6 @@ pub trait Write { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1360,7 +1365,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1395,7 +1399,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1459,7 +1462,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + while !bufs.is_empty() { + match self.write_vectored(bufs) { +@@ -1512,7 +1514,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1568,7 +1569,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1603,7 +1603,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1619,7 +1618,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1657,7 +1655,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1696,7 +1693,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1708,29 +1704,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1809,7 +1802,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1850,7 +1843,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1872,7 +1864,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1932,7 +1923,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1995,7 +1985,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2036,7 +2025,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2078,7 +2066,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2093,7 +2080,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2119,7 +2105,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2142,7 +2127,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2169,20 +2153,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2210,7 +2191,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2235,7 +2216,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2270,7 +2250,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2298,7 +2277,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2323,7 +2301,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2348,7 +2325,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2377,13 +2353,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2401,6 +2375,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2409,7 +2384,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2436,13 +2411,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2466,14 +2439,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2498,13 +2471,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b9d5dc2..07d090e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -190,7 +184,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -203,7 +196,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -222,12 +214,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -251,7 +241,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/39c52225dd06ab06ef75ef97841c66c7d9b6e56c.patch b/patches/39c52225dd06ab06ef75ef97841c66c7d9b6e56c.patch new file mode 100644 index 0000000..a76e798 --- /dev/null +++ b/patches/39c52225dd06ab06ef75ef97841c66c7d9b6e56c.patch @@ -0,0 +1,1850 @@ +diff --git a/buffered.rs b/buffered.rs +index 8862226..7898006 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -222,7 +215,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -240,7 +232,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -260,7 +251,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -298,7 +288,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -318,7 +307,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -331,7 +319,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -442,7 +429,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -477,7 +463,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -492,7 +477,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -510,7 +494,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -557,7 +540,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -577,7 +559,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -595,7 +576,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -616,7 +596,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -640,7 +619,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -649,7 +627,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -685,7 +662,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -698,7 +674,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -708,7 +683,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -747,7 +721,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -782,28 +755,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -874,7 +836,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -895,7 +856,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -916,7 +876,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -937,7 +896,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -962,7 +920,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -990,7 +947,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -998,7 +954,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1104,7 +1059,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index f36aa18..89d0701 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -268,7 +259,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -279,15 +270,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -320,6 +320,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -348,6 +349,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -360,7 +362,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -378,7 +379,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -394,7 +395,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -410,8 +411,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index 3b55d9b..c754d1f 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -432,12 +396,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -466,8 +429,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -493,10 +455,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -509,8 +470,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -518,13 +477,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -532,34 +489,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index b7f82e6..c857f83 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -25,11 +29,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -40,7 +46,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -67,14 +72,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -97,7 +101,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -114,11 +118,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -129,7 +135,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -156,14 +162,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -207,7 +213,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -265,6 +270,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -274,7 +280,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -292,7 +298,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -333,7 +338,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 83c492f..0efb445 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,53 +257,43 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -330,6 +320,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -357,10 +348,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -496,7 +489,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning + /// how many bytes were read. +@@ -563,7 +555,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -574,7 +565,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -601,7 +591,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -654,7 +643,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -697,7 +686,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -760,7 +749,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -814,7 +802,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -856,7 +843,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -894,7 +880,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -933,7 +918,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -942,16 +926,60 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -964,10 +992,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1002,7 +1029,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1026,7 +1052,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1036,7 +1061,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1049,12 +1073,10 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1067,10 +1089,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1104,7 +1125,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1128,7 +1148,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1139,13 +1158,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1159,21 +1176,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1227,7 +1241,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. + /// +@@ -1275,7 +1288,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1286,7 +1298,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1314,7 +1325,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1349,7 +1359,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1402,7 +1411,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1458,7 +1466,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1493,7 +1500,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1509,7 +1515,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1547,7 +1552,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1586,7 +1590,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1598,29 +1601,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1699,7 +1699,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1740,7 +1740,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1762,7 +1761,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1818,7 +1816,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1877,7 +1874,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1918,7 +1914,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -1960,7 +1955,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -1975,7 +1969,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2001,7 +1994,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2024,7 +2016,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2051,20 +2042,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2092,7 +2080,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2117,7 +2105,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2152,7 +2139,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2180,7 +2166,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2205,7 +2190,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2230,7 +2214,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2259,13 +2242,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2283,6 +2264,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2291,7 +2273,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2318,13 +2300,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2348,14 +2328,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2380,13 +2360,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b09161b..e52119e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -185,7 +179,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -217,12 +209,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -241,7 +231,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/3cecd6003b3eb15168421084a27223596517899c.patch b/patches/3cecd6003b3eb15168421084a27223596517899c.patch new file mode 100644 index 0000000..1dd03c0 --- /dev/null +++ b/patches/3cecd6003b3eb15168421084a27223596517899c.patch @@ -0,0 +1,1893 @@ +diff --git a/buffered.rs b/buffered.rs +index b4c91cc..3c3cad2 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -197,7 +191,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -221,7 +214,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -239,7 +231,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -259,7 +250,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -301,7 +291,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -321,7 +310,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -334,7 +322,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -445,7 +432,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -480,7 +466,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -495,7 +480,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -513,7 +497,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -560,7 +543,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -580,7 +562,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -598,7 +579,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -618,7 +598,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -642,7 +621,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -651,7 +629,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -691,7 +668,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -704,7 +680,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -714,7 +689,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -753,7 +727,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -788,28 +761,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -880,7 +842,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -901,7 +862,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -922,7 +882,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -943,7 +902,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -968,7 +926,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -996,7 +953,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -1004,7 +960,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1105,7 +1060,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index f4db5f8..4f20b8a 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -272,7 +263,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -283,15 +274,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -324,6 +324,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -352,6 +353,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -364,7 +366,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -387,7 +388,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -408,7 +409,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -429,8 +430,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index f7248e7..f7311ad 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,12 +143,10 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -165,7 +154,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -174,7 +162,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -205,7 +192,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -248,36 +234,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -303,7 +270,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -334,7 +300,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -368,12 +333,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -437,12 +401,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -471,8 +434,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -498,10 +460,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -514,8 +475,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -523,13 +482,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -537,34 +494,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 01dff0b..eb78a0f 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -30,11 +34,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -45,7 +51,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -77,14 +82,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -107,7 +111,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -129,11 +133,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -144,7 +150,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -176,14 +182,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -227,7 +233,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -290,6 +295,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -299,7 +305,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -317,7 +323,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -363,7 +368,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index d5af4f2..25319b8 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -258,54 +258,44 @@ + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + // ignore-tidy-filelength + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::mem; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++use core::mem; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -332,6 +322,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -359,10 +350,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -498,7 +491,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -571,7 +563,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -583,7 +574,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -596,7 +586,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -623,7 +612,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -676,7 +664,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -719,7 +707,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -782,7 +770,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -836,7 +823,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -878,7 +864,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -916,7 +901,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -955,7 +939,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -964,22 +947,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -992,10 +1017,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1030,7 +1054,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1054,7 +1077,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1064,7 +1086,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1077,18 +1098,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1101,10 +1118,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1138,7 +1154,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1162,7 +1177,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1173,13 +1187,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1193,21 +1205,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1261,7 +1270,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1310,7 +1318,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1321,7 +1328,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1334,7 +1340,6 @@ pub trait Write { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1362,7 +1367,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1397,7 +1401,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1461,7 +1464,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + while !bufs.is_empty() { + match self.write_vectored(bufs) { +@@ -1514,7 +1516,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1570,7 +1571,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1605,7 +1605,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1621,7 +1620,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1659,7 +1657,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1698,7 +1695,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1710,29 +1706,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1811,7 +1804,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1852,7 +1845,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1874,7 +1866,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1934,7 +1925,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1997,7 +1987,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2038,7 +2027,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2080,7 +2068,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2095,7 +2082,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2121,7 +2107,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2144,7 +2129,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2171,20 +2155,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2212,7 +2193,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2237,7 +2218,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2272,7 +2252,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2300,7 +2279,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2325,7 +2303,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2350,7 +2327,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2379,13 +2355,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2403,6 +2377,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2411,7 +2386,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2438,13 +2413,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2468,14 +2441,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2500,13 +2473,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b9d5dc2..07d090e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -190,7 +184,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -203,7 +196,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -222,12 +214,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -251,7 +241,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/410550665601a8abe8935f7b55d5732fe4c4224f.patch b/patches/410550665601a8abe8935f7b55d5732fe4c4224f.patch new file mode 100644 index 0000000..8a7f0fa --- /dev/null +++ b/patches/410550665601a8abe8935f7b55d5732fe4c4224f.patch @@ -0,0 +1,2078 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 987371f..d2af8b8 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,6 +1,7 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DEFAULT_BUF_SIZE}; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -42,7 +43,6 @@ use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DE + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -66,7 +66,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -87,7 +86,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -117,7 +115,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -140,7 +137,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -168,7 +164,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -191,7 +186,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -215,7 +209,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -233,7 +226,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -253,7 +245,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -309,7 +300,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -329,7 +319,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -342,7 +331,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index 65bc2fc..46cd6b8 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,9 +1,9 @@ +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; +-use crate::mem; ++use core::mem; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -65,7 +65,6 @@ use crate::mem; + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -87,7 +86,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -105,7 +103,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -200,7 +197,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -220,7 +216,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -238,7 +233,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -270,7 +264,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -294,7 +287,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -325,7 +317,6 @@ impl BufWriter { + /// assert_eq!(recovered_writer.len(), 0); + /// assert_eq!(&buffered_data.unwrap(), b"ata"); + /// ``` +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_raw_parts(mut self) -> (W, Result, WriterPanicked>) { + let buf = mem::take(&mut self.buf); + let buf = if !self.panicked { Ok(buf) } else { Err(WriterPanicked { buf }) }; +@@ -333,7 +324,6 @@ impl BufWriter { + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + /// Error returned for the buffered data from `BufWriter::into_raw_parts`, when the underlying + /// writer has previously panicked. Contains the (possibly partly written) buffered data. + /// +@@ -367,7 +357,6 @@ pub struct WriterPanicked { + impl WriterPanicked { + /// Returns the perhaps-unwritten data. Some of this data may have been written by the + /// panicking call(s) to the underlying writer, so simply writing it again is not a good idea. +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_inner(self) -> Vec { + self.buf + } +@@ -376,22 +365,12 @@ impl WriterPanicked { + "BufWriter inner writer panicked, what data remains unwritten is not known"; + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] +-impl error::Error for WriterPanicked { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- Self::DESCRIPTION +- } +-} +- +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Display for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + write!(f, "{}", Self::DESCRIPTION) + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Debug for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("WriterPanicked") +@@ -400,7 +379,6 @@ impl fmt::Debug for WriterPanicked { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -497,7 +475,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -510,7 +487,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -521,7 +497,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index d0c859d..a052adf 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index 6549781..0dc7440 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,7 +119,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } +@@ -143,7 +139,6 @@ impl IntoInnerError { + /// let err = into_inner_err.into_error(); + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_error(self) -> Error { + self.1 + } +@@ -167,28 +162,17 @@ impl IntoInnerError { + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// assert_eq!(recovered_writer.buffer(), b"t be actually written"); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_parts(self) -> (Error, W) { + (self.1, self.0) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/copy.rs b/copy.rs +index 3780f20..9c52ecc 100644 +--- a/copy.rs ++++ b/copy.rs +@@ -1,5 +1,6 @@ +-use super::{BufWriter, ErrorKind, Read, Result, Write, DEFAULT_BUF_SIZE}; +-use crate::mem::MaybeUninit; ++use super::{ErrorKind, Read, Result, Write, DEFAULT_BUF_SIZE}; ++#[cfg(feature = "collections")] use super::BufWriter; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,19 +40,12 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> Result + where + R: Read, + W: Write, + { +- cfg_if::cfg_if! { +- if #[cfg(any(target_os = "linux", target_os = "android"))] { +- crate::sys::kernel_copy::copy_spec(reader, writer) +- } else { +- generic_copy(reader, writer) +- } +- } ++ generic_copy(reader, writer) + } + + /// The userspace read-write-loop implementation of `io::copy` that is used when +@@ -76,6 +70,7 @@ impl BufferedCopySpec for W { + } + } + ++#[cfg(feature = "collections")] + impl BufferedCopySpec for BufWriter { + fn copy_to(reader: &mut R, writer: &mut Self) -> Result { + if writer.capacity() < DEFAULT_BUF_SIZE { +diff --git a/cursor.rs b/cursor.rs +index bbee2cc..dc75216 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,8 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,8 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn get_ref(&self) -> &T { + &self.inner + } +@@ -152,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -176,8 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn position(&self) -> u64 { + self.pos + } +@@ -199,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -245,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -274,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -285,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -326,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -354,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -366,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -389,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -410,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -431,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 00bf8b9..5c0e7cd 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -216,7 +222,6 @@ impl BufRead for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -279,6 +284,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -288,7 +294,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -310,7 +316,6 @@ impl BufRead for &[u8] { + /// If the number of bytes to be written exceeds the size of the slice, write operations will + /// return short writes: ultimately, `Ok(0)`; in this situation, `write_all` returns an error of + /// kind `ErrorKind::WriteZero`. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -356,7 +361,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index db3b0e2..6e3a4c5 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -246,58 +246,48 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::copy::copy; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[unstable(feature = "internal_output_capture", issue = "none")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::set_output_capture; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + pub(crate) mod copy; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -324,6 +314,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -351,10 +342,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -505,7 +498,6 @@ pub(crate) fn default_read_exact(this: &mut R, mut buf: &mut [ + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -576,7 +568,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -588,7 +579,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -601,7 +591,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -625,7 +614,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -677,7 +665,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -720,7 +708,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -784,7 +772,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, buf: &mut [u8]) -> Result<()> { + default_read_exact(self, buf) + } +@@ -823,7 +810,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -860,7 +846,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -898,7 +883,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -937,7 +921,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -987,29 +970,71 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +-#[unstable(feature = "io_read_to_string", issue = "80218")] ++#[cfg(feature="collections")] + pub fn read_to_string(reader: &mut R) -> Result { + let mut buf = String::new(); + reader.read_to_string(&mut buf)?; + Ok(buf) + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1022,10 +1047,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1060,7 +1084,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1084,7 +1107,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1094,7 +1116,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1107,18 +1128,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1131,10 +1148,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1168,7 +1184,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1192,7 +1207,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1203,13 +1217,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1223,21 +1235,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1291,7 +1300,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1338,7 +1346,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1351,7 +1358,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1366,7 +1372,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1394,7 +1399,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1428,7 +1432,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1490,7 +1493,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1543,7 +1545,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1599,7 +1600,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1634,7 +1634,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1648,7 +1647,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1685,7 +1683,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_stream_len", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1722,7 +1719,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "seek_convenience", since = "1.51.0")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1732,29 +1728,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1830,7 +1823,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1871,7 +1864,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1893,7 +1885,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1950,7 +1941,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -2013,7 +2003,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2051,7 +2040,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2088,7 +2076,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2103,7 +2090,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2129,7 +2115,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2152,7 +2137,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2179,20 +2163,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2220,7 +2201,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2245,7 +2226,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2278,7 +2258,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2306,7 +2285,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2331,7 +2309,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2356,7 +2333,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2385,13 +2361,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2409,6 +2383,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2417,7 +2392,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2444,13 +2419,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2474,14 +2447,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2506,13 +2479,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index d806431..6b9791a 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index e43ce4c..e1f6fbc 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,14 +3,14 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write}; ++use core::fmt; ++use crate::io::{self, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; + + /// A reader which is always at EOF. + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -30,13 +30,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -48,7 +45,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -58,7 +56,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "empty_seek", since = "1.51.0")] + impl Seek for Empty { + fn seek(&mut self, _pos: SeekFrom) -> io::Result { + Ok(0) +@@ -73,7 +70,6 @@ impl Seek for Empty { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -84,7 +80,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -103,13 +98,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -139,7 +131,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -150,7 +141,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -171,13 +161,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -201,7 +188,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -225,7 +211,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/413ab57c0210ecbe92298c53ec4e1e39f97e4e4c.patch b/patches/413ab57c0210ecbe92298c53ec4e1e39f97e4e4c.patch new file mode 100644 index 0000000..42eb1e2 --- /dev/null +++ b/patches/413ab57c0210ecbe92298c53ec4e1e39f97e4e4c.patch @@ -0,0 +1,1797 @@ +diff --git a/buffered.rs b/buffered.rs +index 557da17..93235d4 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,13 +1,13 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, Initializer, DEFAULT_BUF_SIZE, Error, ErrorKind, SeekFrom, IoSlice, + IoSliceMut}; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -49,7 +49,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -73,7 +72,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -94,7 +92,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -129,7 +126,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { &self.inner } + + /// Gets a mutable reference to the underlying reader. +@@ -150,7 +146,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { &mut self.inner } + + /// Returns a reference to the internally buffered data. +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { self.inner } + + /// Invalidates all data in the internal buffer. +@@ -214,7 +207,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -234,7 +226,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -272,7 +263,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -292,7 +282,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader where R: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufReader") +@@ -302,7 +291,6 @@ impl fmt::Debug for BufReader where R: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -413,7 +401,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -448,7 +435,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -463,7 +449,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -481,7 +466,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { + inner: Some(inner), +@@ -530,7 +514,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.as_ref().unwrap() } + + /// Gets a mutable reference to the underlying writer. +@@ -548,7 +531,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.as_mut().unwrap() } + + /// Returns a reference to the internally buffered data. +@@ -564,7 +546,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -588,7 +569,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -597,7 +577,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -633,7 +612,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufWriter") +@@ -643,7 +621,6 @@ impl fmt::Debug for BufWriter where W: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -653,7 +630,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -692,7 +668,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { &self.1 } + + /// Returns the buffered writer instance which generated the error. +@@ -725,23 +700,13 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { self.0 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { iie.1 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -812,7 +777,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -833,7 +797,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -854,7 +817,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { + inner: BufWriter::with_capacity(capacity, inner), +@@ -878,7 +840,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.get_ref() } + + /// Gets a mutable reference to the underlying writer. +@@ -901,7 +862,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.get_mut() } + + /// Unwraps this `LineWriter`, returning the underlying writer. +@@ -927,7 +887,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { +@@ -938,7 +897,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -983,7 +941,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("LineWriter") +diff --git a/cursor.rs b/cursor.rs +index a94176e..7768d39 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Initializer, SeekFrom, Error, ErrorKind, IoSlice, IoSliceMut}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { self.inner } + + /// Gets a reference to the underlying value in this cursor. +@@ -128,7 +125,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { &self.inner } + + /// Gets a mutable reference to the underlying value in this cursor. +@@ -147,7 +143,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { &mut self.inner } + + /// Returns the current position of this cursor. +@@ -169,7 +164,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { self.pos } + + /// Sets the position of this cursor. +@@ -189,11 +183,9 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { self.pos = pos; } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor where T: AsRef<[u8]> { + fn seek(&mut self, style: SeekFrom) -> io::Result { + let (base_pos, offset) = match style { +@@ -222,10 +214,9 @@ impl io::Seek for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor where T: AsRef<[u8]> { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -244,7 +235,7 @@ impl Read for Cursor where T: AsRef<[u8]> { + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -255,12 +246,16 @@ impl Read for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor where T: AsRef<[u8]> { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++impl Cursor where T: AsRef<[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor where T: AsRef<[u8]> { ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { self.get_buf() } + fn consume(&mut self, amt: usize) { self.pos += amt as u64; } + } + +@@ -292,6 +287,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new(ErrorKind::InvalidInput, +@@ -318,6 +314,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -331,7 +328,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -347,7 +343,7 @@ impl Write for Cursor<&mut [u8]> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -361,7 +357,7 @@ impl Write for Cursor<&mut Vec> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -375,8 +371,8 @@ impl Write for Cursor> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index c29a68e..c94d8c5 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,13 @@ +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; +-use crate::convert::From; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++use core::convert::Into; ++use core::fmt; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++use core::result; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; ++use core::convert::From; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +43,6 @@ use crate::convert::From; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +56,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +69,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +90,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +130,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +142,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +156,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +186,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -245,14 +230,13 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error +- where E: Into> ++ where E: Into + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { + repr: Repr::Custom(Box::new(Custom { + kind, +@@ -261,24 +245,6 @@ impl Error { + } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -304,7 +270,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -335,7 +300,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -369,12 +333,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error+Send+Sync+'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -440,12 +403,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error+Send+Sync+'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -474,8 +436,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -501,10 +462,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -516,22 +476,18 @@ impl fmt::Debug for Repr { + match *self { + Repr::Os(code) => + fmt.debug_struct("Os") +- .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)).finish(), ++ .field("code", &code).finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), + } + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -539,33 +495,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index c959f2d..b645bc8 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,13 +1,15 @@ +-use crate::cmp; +-use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, BufRead, Error, ErrorKind, +- IoSliceMut, IoSlice}; +-use crate::fmt; +-use crate::mem; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++use core::cmp; ++use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, Error, ErrorKind, IoSliceMut, IoSlice}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::fmt; ++use core::mem; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -24,11 +26,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -39,7 +43,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -62,12 +65,11 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -86,7 +88,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -103,11 +105,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -118,7 +122,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -141,12 +145,12 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -186,7 +190,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -245,6 +248,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -254,7 +258,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(*self) } +@@ -268,7 +272,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -307,7 +310,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index be364a1..abbf09f 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,50 +257,38 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::slice; +-use crate::str; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(feature="collections")] use collections::string::String; ++use core::str; ++#[cfg(feature="collections")] use collections::vec::Vec; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::slice; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++ ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Result, Error, ErrorKind}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, sink, Sink, empty, Empty, repeat, Repeat}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stdin, stdout, stderr, Stdin, Stdout, Stderr}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StdoutLock, StderrLock, StdinLock}; +-#[unstable(feature = "print_internals", issue = "0")] +-pub use self::stdio::{_print, _eprint}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; + + pub mod prelude; +-mod buffered; ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + mod util; +-mod stdio; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { buf: &'a mut Vec, len: usize } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { self.buf.set_len(self.len); } +@@ -325,6 +313,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where F: FnOnce(&mut Vec) -> Result + { +@@ -352,10 +341,12 @@ fn append_to_string(buf: &mut String, f: F) -> Result + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -497,7 +488,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -565,7 +555,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -576,7 +565,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -603,7 +591,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -656,7 +643,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -699,7 +686,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -762,7 +749,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -814,7 +800,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + + /// Transforms this `Read` instance to an [`Iterator`] over its bytes. +@@ -851,7 +836,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes where Self: Sized { + Bytes { inner: self } + } +@@ -886,7 +870,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain where Self: Sized { + Chain { first: self, second: next, done_first: false } + } +@@ -922,22 +905,64 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take where Self: Sized { + Take { inner: self, limit: limit } + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -950,10 +975,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -989,7 +1013,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1013,7 +1036,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1023,7 +1045,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1036,11 +1057,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1053,10 +1072,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1091,7 +1109,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(mem::replace(&mut bufs, &mut []), 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1115,7 +1132,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1126,13 +1142,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1146,21 +1160,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1214,7 +1225,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1263,7 +1273,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1274,7 +1283,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1302,7 +1310,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1335,7 +1342,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1387,7 +1393,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1443,7 +1448,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + } + +@@ -1473,7 +1477,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1489,7 +1492,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1527,7 +1529,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1566,7 +1567,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1578,29 +1578,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + -> Result { + let mut read = 0; +@@ -1680,7 +1677,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1721,7 +1718,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1743,7 +1739,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1799,7 +1794,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1858,7 +1852,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1899,7 +1892,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split where Self: Sized { + Split { buf: self, delim: byte } + } +@@ -1938,7 +1930,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines where Self: Sized { + Lines { buf: self } + } +@@ -1950,7 +1941,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -1976,7 +1966,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -1999,7 +1988,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2026,13 +2014,11 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain") +@@ -2042,7 +2028,6 @@ impl fmt::Debug for Chain { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2074,7 +2059,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2101,7 +2086,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2136,7 +2120,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { self.limit } + + /// Sets the number of bytes that can be read before this instance will +@@ -2162,7 +2145,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2187,7 +2169,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2212,7 +2193,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2241,13 +2221,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2265,6 +2243,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2273,7 +2252,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2300,13 +2279,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2330,14 +2307,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2362,13 +2339,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 2e19edf..66294a3 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Write, Seek}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{Read, Write, BufRead, Seek}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index 33cc87e..75b8032 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, Read, Initializer, Write, ErrorKind, BufRead, IoSlice, IoSliceMut}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, Read, Initializer, Write, ErrorKind, IoSlice, IoSliceMut}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where R: Read, W: Write + { +@@ -70,7 +70,6 @@ pub fn copy(reader: &mut R, writer: &mut W) -> io::Result< + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { _priv: () } + + /// Constructs a new handle to an empty reader. +@@ -90,10 +89,8 @@ pub struct Empty { _priv: () } + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { Empty { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { Ok(0) } +@@ -103,7 +100,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(&[]) } +@@ -111,7 +109,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -124,7 +121,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { byte: u8 } + + /// Creates an instance of a reader that infinitely repeats one byte. +@@ -141,10 +137,8 @@ pub struct Repeat { byte: u8 } + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { Repeat { byte } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -169,7 +163,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -182,7 +175,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { _priv: () } + + /// Creates an instance of a writer which will successfully consume all data. +@@ -199,10 +191,8 @@ pub struct Sink { _priv: () } + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { Sink { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { Ok(buf.len()) } +@@ -217,7 +207,6 @@ impl Write for Sink { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/4436c9d35498e7ae3da261f6141d6d73b915e1e8.patch b/patches/4436c9d35498e7ae3da261f6141d6d73b915e1e8.patch new file mode 100644 index 0000000..2366dc7 --- /dev/null +++ b/patches/4436c9d35498e7ae3da261f6141d6d73b915e1e8.patch @@ -0,0 +1,1817 @@ +diff --git a/buffered.rs b/buffered.rs +index 8e81b29..b042f36 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -216,7 +209,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -236,7 +228,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -274,7 +265,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -294,7 +284,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -307,7 +296,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -418,7 +406,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -453,7 +440,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -468,7 +454,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -486,7 +471,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -533,7 +517,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -553,7 +536,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -571,7 +553,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -595,7 +576,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -604,7 +584,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -640,7 +619,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -653,7 +631,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -663,7 +640,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -702,7 +678,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -737,27 +712,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -828,7 +793,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -849,7 +813,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -870,7 +833,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -891,7 +853,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -916,7 +877,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -944,7 +904,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -952,7 +911,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -996,7 +954,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index a94176e..7768d39 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Initializer, SeekFrom, Error, ErrorKind, IoSlice, IoSliceMut}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { self.inner } + + /// Gets a reference to the underlying value in this cursor. +@@ -128,7 +125,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { &self.inner } + + /// Gets a mutable reference to the underlying value in this cursor. +@@ -147,7 +143,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { &mut self.inner } + + /// Returns the current position of this cursor. +@@ -169,7 +164,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { self.pos } + + /// Sets the position of this cursor. +@@ -189,11 +183,9 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { self.pos = pos; } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor where T: AsRef<[u8]> { + fn seek(&mut self, style: SeekFrom) -> io::Result { + let (base_pos, offset) = match style { +@@ -222,10 +214,9 @@ impl io::Seek for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor where T: AsRef<[u8]> { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -244,7 +235,7 @@ impl Read for Cursor where T: AsRef<[u8]> { + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -255,12 +246,16 @@ impl Read for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor where T: AsRef<[u8]> { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++impl Cursor where T: AsRef<[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor where T: AsRef<[u8]> { ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { self.get_buf() } + fn consume(&mut self, amt: usize) { self.pos += amt as u64; } + } + +@@ -292,6 +287,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new(ErrorKind::InvalidInput, +@@ -318,6 +314,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -331,7 +328,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -347,7 +343,7 @@ impl Write for Cursor<&mut [u8]> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -361,7 +357,7 @@ impl Write for Cursor<&mut Vec> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -375,8 +371,8 @@ impl Write for Cursor> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index c20bd30..99af4d1 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -434,12 +398,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -468,8 +431,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -495,10 +457,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -511,8 +472,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -520,13 +479,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -534,33 +491,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index b7f82e6..c857f83 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -25,11 +29,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -40,7 +46,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -67,14 +72,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -97,7 +101,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -114,11 +118,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -129,7 +135,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -156,14 +162,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -207,7 +213,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -265,6 +270,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -274,7 +280,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -292,7 +298,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -333,7 +338,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 20c1c5c..0f4343d 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,53 +257,43 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "0")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -330,6 +320,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -357,10 +348,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -496,7 +489,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -564,7 +556,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -575,7 +566,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -602,7 +592,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -655,7 +644,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -698,7 +687,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -761,7 +750,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -815,7 +803,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -857,7 +844,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -895,7 +881,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -934,7 +919,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -943,16 +927,59 @@ pub trait Read { + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -965,10 +992,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1004,7 +1030,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1028,7 +1053,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1038,7 +1062,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1051,11 +1074,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1068,10 +1089,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1106,7 +1126,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(mem::replace(&mut bufs, &mut []), 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1130,7 +1149,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1141,13 +1159,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1161,21 +1177,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1229,7 +1242,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1278,7 +1290,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1289,7 +1300,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1317,7 +1327,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1350,7 +1359,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1403,7 +1411,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1459,7 +1466,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1494,7 +1500,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1510,7 +1515,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1548,7 +1552,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1587,7 +1590,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1599,29 +1601,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1700,7 +1699,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1741,7 +1740,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1763,7 +1761,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1819,7 +1816,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1878,7 +1874,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1919,7 +1914,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -1961,7 +1955,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -1976,7 +1969,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2002,7 +1994,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2025,7 +2016,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2052,20 +2042,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2093,7 +2080,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2118,7 +2105,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2153,7 +2139,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2181,7 +2166,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2206,7 +2190,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2231,7 +2214,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2260,13 +2242,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2284,6 +2264,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2292,7 +2273,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2319,13 +2300,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2349,14 +2328,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2381,13 +2360,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b09161b..e52119e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -185,7 +179,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -217,12 +209,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -241,7 +231,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/4646a88b7a1e68326d092b9cbbbbdd616a51077f.patch b/patches/4646a88b7a1e68326d092b9cbbbbdd616a51077f.patch new file mode 100644 index 0000000..a892120 --- /dev/null +++ b/patches/4646a88b7a1e68326d092b9cbbbbdd616a51077f.patch @@ -0,0 +1,1832 @@ +diff --git a/buffered.rs b/buffered.rs +index fee5a4e..de9bc11 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -216,7 +209,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -236,7 +228,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -274,7 +265,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -294,7 +284,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -307,7 +296,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -418,7 +406,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -453,7 +440,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -468,7 +454,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -486,7 +471,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -533,7 +517,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -553,7 +536,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -571,7 +553,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -595,7 +576,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -604,7 +584,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -640,7 +619,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -653,7 +631,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -663,7 +640,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -702,7 +678,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -737,28 +712,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -829,7 +793,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -850,7 +813,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -871,7 +833,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -892,7 +853,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -917,7 +877,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -945,7 +904,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -953,7 +911,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1059,7 +1016,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index 9787cbb..1cf83d3 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -268,7 +259,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -279,15 +270,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -320,6 +320,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -348,6 +349,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -360,7 +362,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -378,7 +379,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -394,7 +395,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -410,8 +411,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index 3b55d9b..c754d1f 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -432,12 +396,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -466,8 +429,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -493,10 +455,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -509,8 +470,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -518,13 +477,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -532,34 +489,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index b7f82e6..c857f83 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -25,11 +29,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -40,7 +46,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -67,14 +72,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -97,7 +101,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -114,11 +118,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -129,7 +135,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -156,14 +162,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -207,7 +213,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -265,6 +270,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -274,7 +280,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -292,7 +298,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -333,7 +338,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 95c8934..b29907e 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,53 +257,43 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -330,6 +320,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -357,10 +348,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -496,7 +489,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -564,7 +556,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -575,7 +566,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -602,7 +592,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -655,7 +644,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -698,7 +687,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -761,7 +750,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -815,7 +803,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -857,7 +844,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -895,7 +881,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -934,7 +919,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -943,16 +927,59 @@ pub trait Read { + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -965,10 +992,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1003,7 +1029,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1027,7 +1052,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1037,7 +1061,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1050,11 +1073,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1067,10 +1088,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1104,7 +1124,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1128,7 +1147,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1139,13 +1157,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1159,21 +1175,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1227,7 +1240,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1276,7 +1288,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1287,7 +1298,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1315,7 +1325,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1348,7 +1357,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1401,7 +1409,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1457,7 +1464,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1492,7 +1498,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1508,7 +1513,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1546,7 +1550,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1585,7 +1588,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1597,29 +1599,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1698,7 +1697,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1739,7 +1738,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1761,7 +1759,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1817,7 +1814,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1876,7 +1872,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1917,7 +1912,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -1959,7 +1953,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -1974,7 +1967,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2000,7 +1992,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2023,7 +2014,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2050,20 +2040,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2091,7 +2078,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2116,7 +2103,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2151,7 +2137,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2179,7 +2164,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2204,7 +2188,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2229,7 +2212,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2258,13 +2240,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2282,6 +2262,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2290,7 +2271,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2317,13 +2298,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2347,14 +2326,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2379,13 +2358,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b09161b..e52119e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -185,7 +179,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -217,12 +209,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -241,7 +231,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/471dd52d7710dcad5fec0cd731b836b02ba4a8f4.patch b/patches/471dd52d7710dcad5fec0cd731b836b02ba4a8f4.patch new file mode 100644 index 0000000..ecd7150 --- /dev/null +++ b/patches/471dd52d7710dcad5fec0cd731b836b02ba4a8f4.patch @@ -0,0 +1,1893 @@ +diff --git a/buffered.rs b/buffered.rs +index b4c91cc..3c3cad2 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -197,7 +191,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -221,7 +214,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -239,7 +231,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -259,7 +250,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -301,7 +291,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -321,7 +310,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -334,7 +322,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -445,7 +432,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -480,7 +466,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -495,7 +480,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -513,7 +497,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -560,7 +543,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -580,7 +562,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -598,7 +579,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -618,7 +598,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -642,7 +621,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -651,7 +629,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -691,7 +668,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -704,7 +680,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -714,7 +689,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -753,7 +727,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -788,28 +761,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -880,7 +842,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -901,7 +862,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -922,7 +882,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -943,7 +902,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -968,7 +926,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -996,7 +953,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -1004,7 +960,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1105,7 +1060,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index f4db5f8..4f20b8a 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -272,7 +263,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -283,15 +274,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -324,6 +324,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -352,6 +353,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -364,7 +366,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -387,7 +388,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -408,7 +409,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -429,8 +430,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index f7248e7..f7311ad 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,12 +143,10 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -165,7 +154,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -174,7 +162,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -205,7 +192,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -248,36 +234,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -303,7 +270,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -334,7 +300,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -368,12 +333,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -437,12 +401,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -471,8 +434,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -498,10 +460,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -514,8 +475,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -523,13 +482,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -537,34 +494,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 01dff0b..eb78a0f 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -30,11 +34,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -45,7 +51,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -77,14 +82,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -107,7 +111,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -129,11 +133,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -144,7 +150,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -176,14 +182,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -227,7 +233,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -290,6 +295,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -299,7 +305,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -317,7 +323,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -363,7 +368,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 797318d..f40b9b5 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -247,54 +247,44 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::mem; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++use core::mem; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -321,6 +311,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -348,10 +339,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -485,7 +478,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -556,7 +548,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -568,7 +559,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -581,7 +571,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -605,7 +594,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -657,7 +645,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -700,7 +688,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -764,7 +752,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -818,7 +805,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -856,7 +842,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -894,7 +879,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -933,7 +917,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -942,22 +925,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -970,10 +995,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1008,7 +1032,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1032,7 +1055,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1042,7 +1064,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1055,18 +1076,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1079,10 +1096,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1116,7 +1132,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1140,7 +1155,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1151,13 +1165,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1171,21 +1183,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1239,7 +1248,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Self::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1284,7 +1292,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1295,7 +1302,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1308,7 +1314,6 @@ pub trait Write { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1336,7 +1341,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1370,7 +1374,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1433,7 +1436,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + while !bufs.is_empty() { + match self.write_vectored(bufs) { +@@ -1483,7 +1485,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1539,7 +1540,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1574,7 +1574,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1590,7 +1589,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1628,7 +1626,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1667,7 +1664,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1679,29 +1675,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1780,7 +1773,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1821,7 +1814,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1843,7 +1835,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: Self::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1903,7 +1894,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1966,7 +1956,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2007,7 +1996,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2046,7 +2034,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2061,7 +2048,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2087,7 +2073,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2110,7 +2095,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2137,20 +2121,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2178,7 +2159,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2203,7 +2184,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2236,7 +2216,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2264,7 +2243,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2289,7 +2267,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2314,7 +2291,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2343,13 +2319,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2367,6 +2341,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2375,7 +2350,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2402,13 +2377,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2432,14 +2405,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2464,13 +2437,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b9d5dc2..07d090e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -190,7 +184,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -203,7 +196,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -222,12 +214,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -251,7 +241,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/4e27ed3af19e604d7b65e130145fcecdc69fba7a.patch b/patches/4e27ed3af19e604d7b65e130145fcecdc69fba7a.patch new file mode 100644 index 0000000..1cba0a7 --- /dev/null +++ b/patches/4e27ed3af19e604d7b65e130145fcecdc69fba7a.patch @@ -0,0 +1,2010 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 8bae3da..c6a45f8 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,6 +1,7 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DEFAULT_BUF_SIZE}; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -42,7 +43,6 @@ use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DE + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -66,7 +66,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -87,7 +86,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -117,7 +115,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -140,7 +137,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -168,7 +164,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -191,7 +186,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -215,7 +209,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -233,7 +226,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -253,7 +245,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -309,7 +300,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -329,7 +319,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -342,7 +331,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index 3b33998..d20db36 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,7 +1,8 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -63,7 +64,6 @@ use crate::io::{ + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -85,7 +85,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -103,7 +102,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -198,7 +196,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -218,7 +215,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -236,7 +232,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -256,7 +251,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -280,7 +274,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -289,7 +282,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -386,7 +378,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -399,7 +390,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -410,7 +400,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index d0c859d..a052adf 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index 6549781..0dc7440 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,7 +119,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } +@@ -143,7 +139,6 @@ impl IntoInnerError { + /// let err = into_inner_err.into_error(); + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_error(self) -> Error { + self.1 + } +@@ -167,28 +162,17 @@ impl IntoInnerError { + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// assert_eq!(recovered_writer.buffer(), b"t be actually written"); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_parts(self) -> (Error, W) { + (self.1, self.0) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/copy.rs b/copy.rs +index b88bca2..7593702 100644 +--- a/copy.rs ++++ b/copy.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, ErrorKind, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,19 +39,12 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, + W: Write, + { +- cfg_if::cfg_if! { +- if #[cfg(any(target_os = "linux", target_os = "android"))] { +- crate::sys::kernel_copy::copy_spec(reader, writer) +- } else { +- generic_copy(reader, writer) +- } +- } ++ generic_copy(reader, writer) + } + + /// The general read-write-loop implementation of +diff --git a/cursor.rs b/cursor.rs +index bbee2cc..dc75216 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,8 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,8 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn get_ref(&self) -> &T { + &self.inner + } +@@ -152,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -176,8 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn position(&self) -> u64 { + self.pos + } +@@ -199,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -245,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -274,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -285,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -326,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -354,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -366,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -389,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -410,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -431,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 00bf8b9..5c0e7cd 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -216,7 +222,6 @@ impl BufRead for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -279,6 +284,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -288,7 +294,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -310,7 +316,6 @@ impl BufRead for &[u8] { + /// If the number of bytes to be written exceeds the size of the slice, write operations will + /// return short writes: ultimately, `Ok(0)`; in this situation, `write_all` returns an error of + /// kind `ErrorKind::WriteZero`. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -356,7 +361,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index c87a565..138fcf7 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -246,58 +246,48 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::copy::copy; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[unstable(feature = "internal_output_capture", issue = "none")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::set_output_capture; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + pub(crate) mod copy; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -324,6 +314,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -351,10 +342,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -505,7 +498,6 @@ pub(crate) fn default_read_exact(this: &mut R, mut buf: &mut [ + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -576,7 +568,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -588,7 +579,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -601,7 +591,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -625,7 +614,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -677,7 +665,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -720,7 +708,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -784,7 +772,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, buf: &mut [u8]) -> Result<()> { + default_read_exact(self, buf) + } +@@ -823,7 +810,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -860,7 +846,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -898,7 +883,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -937,7 +921,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -987,29 +970,71 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +-#[unstable(feature = "io_read_to_string", issue = "80218")] ++#[cfg(feature="collections")] + pub fn read_to_string(reader: &mut R) -> Result { + let mut buf = String::new(); + reader.read_to_string(&mut buf)?; + Ok(buf) + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1022,10 +1047,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1060,7 +1084,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1084,7 +1107,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1094,7 +1116,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1107,18 +1128,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1131,10 +1148,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1168,7 +1184,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1192,7 +1207,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1203,13 +1217,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1223,21 +1235,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1291,7 +1300,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1338,7 +1346,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1351,7 +1358,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1366,7 +1372,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1394,7 +1399,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1428,7 +1432,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1490,7 +1493,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1543,7 +1545,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1599,7 +1600,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1634,7 +1634,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1648,7 +1647,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1685,7 +1683,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1723,7 +1720,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1733,29 +1729,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1831,7 +1824,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1872,7 +1865,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1894,7 +1886,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1951,7 +1942,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -2014,7 +2004,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2052,7 +2041,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2089,7 +2077,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2104,7 +2091,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2130,7 +2116,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2153,7 +2138,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2180,20 +2164,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2221,7 +2202,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2246,7 +2227,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2279,7 +2259,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2307,7 +2286,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2332,7 +2310,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2357,7 +2334,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2386,13 +2362,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2410,6 +2384,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2418,7 +2393,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2445,13 +2420,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2475,14 +2448,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2507,13 +2480,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index db84545..8e88c3d 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,14 +3,14 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, Initializer, IoSlice, IoSliceMut, Read, Write}; ++use core::fmt; ++use crate::io::{self, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; + + /// A reader which is always at EOF. + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -30,13 +30,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -48,7 +45,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -58,7 +56,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -69,7 +66,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -88,13 +84,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -124,7 +117,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -135,7 +127,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -156,13 +147,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -186,7 +174,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -210,7 +197,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/5304511fbc1f9a0c7340f7f0d037aa4dd13a588f.patch b/patches/5304511fbc1f9a0c7340f7f0d037aa4dd13a588f.patch new file mode 100644 index 0000000..3499f86 --- /dev/null +++ b/patches/5304511fbc1f9a0c7340f7f0d037aa4dd13a588f.patch @@ -0,0 +1,1893 @@ +diff --git a/buffered.rs b/buffered.rs +index b4c91cc..3c3cad2 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -197,7 +191,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -221,7 +214,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -239,7 +231,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -259,7 +250,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -301,7 +291,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -321,7 +310,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -334,7 +322,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -445,7 +432,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -480,7 +466,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -495,7 +480,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -513,7 +497,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -560,7 +543,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -580,7 +562,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -598,7 +579,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -618,7 +598,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -642,7 +621,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -651,7 +629,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -691,7 +668,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -704,7 +680,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -714,7 +689,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -753,7 +727,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -788,28 +761,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -880,7 +842,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -901,7 +862,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -922,7 +882,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -943,7 +902,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -968,7 +926,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -996,7 +953,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -1004,7 +960,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1105,7 +1060,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index f4db5f8..4f20b8a 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -272,7 +263,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -283,15 +274,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -324,6 +324,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -352,6 +353,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -364,7 +366,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -387,7 +388,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -408,7 +409,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -429,8 +430,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index f7248e7..f7311ad 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,12 +143,10 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -165,7 +154,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -174,7 +162,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -205,7 +192,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -248,36 +234,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -303,7 +270,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -334,7 +300,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -368,12 +333,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -437,12 +401,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -471,8 +434,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -498,10 +460,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -514,8 +475,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -523,13 +482,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -537,34 +494,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 01dff0b..eb78a0f 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -30,11 +34,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -45,7 +51,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -77,14 +82,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -107,7 +111,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -129,11 +133,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -144,7 +150,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -176,14 +182,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -227,7 +233,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -290,6 +295,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -299,7 +305,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -317,7 +323,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -363,7 +368,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 717d286..8a46366 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -258,54 +258,44 @@ + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + // ignore-tidy-filelength + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::mem; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++use core::mem; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -332,6 +322,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -359,10 +350,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -498,7 +491,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning + /// how many bytes were read. +@@ -570,7 +562,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -582,7 +573,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -595,7 +585,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -622,7 +611,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -675,7 +663,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -718,7 +706,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -781,7 +769,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -835,7 +822,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -877,7 +863,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -915,7 +900,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -954,7 +938,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -963,22 +946,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -991,10 +1016,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1029,7 +1053,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1053,7 +1076,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1063,7 +1085,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1076,18 +1097,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1100,10 +1117,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1137,7 +1153,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1161,7 +1176,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1172,13 +1186,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1192,21 +1204,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1260,7 +1269,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. + /// +@@ -1308,7 +1316,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1319,7 +1326,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1332,7 +1338,6 @@ pub trait Write { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1360,7 +1365,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1395,7 +1399,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1459,7 +1462,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + while !bufs.is_empty() { + match self.write_vectored(bufs) { +@@ -1512,7 +1514,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1568,7 +1569,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1603,7 +1603,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1619,7 +1618,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1657,7 +1655,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1696,7 +1693,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1708,29 +1704,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1809,7 +1802,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1850,7 +1843,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1872,7 +1864,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1932,7 +1923,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1995,7 +1985,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2036,7 +2025,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2078,7 +2066,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2093,7 +2080,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2119,7 +2105,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2142,7 +2127,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2169,20 +2153,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2210,7 +2191,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2235,7 +2216,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2270,7 +2250,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2298,7 +2277,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2323,7 +2301,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2348,7 +2325,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2377,13 +2353,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2401,6 +2375,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2409,7 +2384,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2436,13 +2411,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2466,14 +2439,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2498,13 +2471,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b9d5dc2..07d090e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -190,7 +184,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -203,7 +196,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -222,12 +214,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -251,7 +241,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/56d288fa46e04cd5faf53d369a1a640a97e2bb08.patch b/patches/56d288fa46e04cd5faf53d369a1a640a97e2bb08.patch new file mode 100644 index 0000000..6646a45 --- /dev/null +++ b/patches/56d288fa46e04cd5faf53d369a1a640a97e2bb08.patch @@ -0,0 +1,1958 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 8fe29f0..e0f677c 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,6 +1,7 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DEFAULT_BUF_SIZE}; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -41,7 +42,6 @@ use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DE + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -65,7 +65,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -86,7 +85,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -116,7 +114,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -139,7 +136,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -167,7 +163,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -190,7 +185,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -214,7 +208,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -232,7 +225,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -252,7 +244,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -294,7 +285,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -314,7 +304,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -327,7 +316,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index 3ec272f..4ff75ab 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,7 +1,8 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -62,7 +63,6 @@ use crate::io::{ + /// [`TcpStream::write`]: Write::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: Write::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -84,7 +84,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -102,7 +101,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -197,7 +195,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -217,7 +214,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -235,7 +231,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -255,7 +250,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -279,7 +273,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -288,7 +281,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -352,7 +344,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -365,7 +356,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -376,7 +366,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index a80d08d..20bd401 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index f9caeaf..c21de5c 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,28 +119,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/cursor.rs b/cursor.rs +index 5733735..0fdd84a 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,7 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -111,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -129,7 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -150,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -196,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -242,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -271,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -282,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -323,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -351,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -363,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -386,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -407,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -428,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 6642610..efbe402 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -230,7 +236,6 @@ impl Write for dyn ::realstd::io::LocalOutput { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -293,6 +298,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -302,7 +308,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -320,7 +326,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -366,7 +371,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index e6efe6e..e647c6b 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -247,57 +247,46 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print, LocalOutput}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-pub(crate) use self::stdio::clone_io; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + +-mod buffered; ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -324,6 +313,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -351,10 +341,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -488,7 +480,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -559,7 +550,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -571,7 +561,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -584,7 +573,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -608,7 +596,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -660,7 +647,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -703,7 +690,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -767,7 +754,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -821,7 +807,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -858,7 +843,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -896,7 +880,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -935,7 +918,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -944,22 +926,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -972,10 +996,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1010,7 +1033,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1034,7 +1056,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1044,7 +1065,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1057,18 +1077,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1081,10 +1097,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1118,7 +1133,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1142,7 +1156,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1153,13 +1166,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1173,21 +1184,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1241,7 +1249,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1288,7 +1295,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1301,7 +1307,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1316,7 +1321,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1344,7 +1348,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1378,7 +1381,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1440,7 +1442,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1493,7 +1494,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1549,7 +1549,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1584,7 +1583,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1598,7 +1596,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1635,7 +1632,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1673,7 +1669,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1683,29 +1678,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1781,7 +1773,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1822,7 +1814,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1844,7 +1835,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1901,7 +1891,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1964,7 +1953,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2003,7 +1991,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2040,7 +2027,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2055,7 +2041,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2081,7 +2066,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2104,7 +2088,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2131,20 +2114,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2172,7 +2152,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2197,7 +2177,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2230,7 +2209,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2258,7 +2236,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2283,7 +2260,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2308,7 +2284,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2337,13 +2312,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2361,6 +2334,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2369,7 +2343,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2396,13 +2370,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2426,14 +2398,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2458,13 +2430,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index dc05b96..aa7ee35 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,9 +3,10 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -45,7 +46,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -81,7 +81,6 @@ where + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -101,12 +100,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -118,7 +115,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -128,7 +126,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -139,7 +136,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -158,12 +154,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -193,7 +187,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -204,7 +197,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -225,12 +217,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -254,7 +244,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -278,7 +267,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/5768385615c61f6c9d63dccfb3548812f1ba1320.patch b/patches/5768385615c61f6c9d63dccfb3548812f1ba1320.patch new file mode 100644 index 0000000..b62be43 --- /dev/null +++ b/patches/5768385615c61f6c9d63dccfb3548812f1ba1320.patch @@ -0,0 +1,1872 @@ +diff --git a/buffered.rs b/buffered.rs +index 8862226..7898006 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -222,7 +215,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -240,7 +232,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -260,7 +251,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -298,7 +288,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -318,7 +307,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -331,7 +319,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -442,7 +429,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -477,7 +463,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -492,7 +477,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -510,7 +494,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -557,7 +540,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -577,7 +559,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -595,7 +576,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -616,7 +596,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -640,7 +619,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -649,7 +627,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -685,7 +662,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -698,7 +674,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -708,7 +683,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -747,7 +721,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -782,28 +755,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -874,7 +836,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -895,7 +856,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -916,7 +876,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -937,7 +896,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -962,7 +920,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -990,7 +947,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -998,7 +954,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1104,7 +1059,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index f36aa18..89d0701 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -268,7 +259,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -279,15 +270,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -320,6 +320,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -348,6 +349,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -360,7 +362,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -378,7 +379,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -394,7 +395,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -410,8 +411,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index 3b55d9b..c754d1f 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -432,12 +396,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -466,8 +429,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -493,10 +455,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -509,8 +470,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -518,13 +477,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -532,34 +489,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index b7f82e6..c857f83 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -25,11 +29,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -40,7 +46,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -67,14 +72,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -97,7 +101,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -114,11 +118,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -129,7 +135,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -156,14 +162,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -207,7 +213,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -265,6 +270,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -274,7 +280,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -292,7 +298,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -333,7 +338,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 5ab8826..028c5e8 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,54 +257,44 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::mem; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++use core::mem; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -331,6 +321,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -358,10 +349,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -497,7 +490,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning + /// how many bytes were read. +@@ -564,7 +556,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -575,7 +566,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -602,7 +592,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -655,7 +644,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -698,7 +687,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -761,7 +750,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -815,7 +803,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -857,7 +844,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -895,7 +881,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -934,7 +919,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -943,22 +927,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -971,10 +997,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1009,7 +1034,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1033,7 +1057,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1043,7 +1066,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1056,18 +1078,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1080,10 +1098,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1117,7 +1134,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1141,7 +1157,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1152,13 +1167,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1172,21 +1185,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1240,7 +1250,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. + /// +@@ -1288,7 +1297,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1299,7 +1307,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1327,7 +1334,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1362,7 +1368,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1426,7 +1431,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + while !bufs.is_empty() { + match self.write_vectored(bufs) { +@@ -1479,7 +1483,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1535,7 +1538,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1570,7 +1572,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1586,7 +1587,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1624,7 +1624,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1663,7 +1662,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1675,29 +1673,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1776,7 +1771,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1817,7 +1812,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1839,7 +1833,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1895,7 +1888,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1954,7 +1946,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1995,7 +1986,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2037,7 +2027,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2052,7 +2041,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2078,7 +2066,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2101,7 +2088,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2128,20 +2114,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2169,7 +2152,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2194,7 +2177,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2229,7 +2211,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2257,7 +2238,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2282,7 +2262,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2307,7 +2286,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2336,13 +2314,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2360,6 +2336,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2368,7 +2345,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2395,13 +2372,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2425,14 +2400,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2457,13 +2432,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b09161b..e52119e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -185,7 +179,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -217,12 +209,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -241,7 +231,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/5acb7f198fa56943a2837583d555896badb5733d.patch b/patches/5acb7f198fa56943a2837583d555896badb5733d.patch new file mode 100644 index 0000000..4a1fa10 --- /dev/null +++ b/patches/5acb7f198fa56943a2837583d555896badb5733d.patch @@ -0,0 +1,1957 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 8fe29f0..e0f677c 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,6 +1,7 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DEFAULT_BUF_SIZE}; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -41,7 +42,6 @@ use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DE + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -65,7 +65,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -86,7 +85,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -116,7 +114,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -139,7 +136,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -167,7 +163,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -190,7 +185,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -214,7 +208,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -232,7 +225,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -252,7 +244,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -294,7 +285,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -314,7 +304,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -327,7 +316,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index 8ce795a..17bc2a1 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,7 +1,8 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -62,7 +63,6 @@ use crate::io::{ + /// [`TcpStream::write`]: Write::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: Write::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -84,7 +84,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -102,7 +101,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -197,7 +195,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -217,7 +214,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -235,7 +231,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -255,7 +250,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -279,7 +273,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -288,7 +281,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -352,7 +344,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -365,7 +356,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -376,7 +366,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index a80d08d..20bd401 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index f9caeaf..c21de5c 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,28 +119,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/cursor.rs b/cursor.rs +index 5733735..0fdd84a 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,7 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -111,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -129,7 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -150,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -196,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -242,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -271,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -282,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -323,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -351,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -363,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -386,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -407,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -428,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index e09e7ba..126a710 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -230,7 +236,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -293,6 +298,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -302,7 +308,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -320,7 +326,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -366,7 +371,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index d9d0380..e647c6b 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -247,55 +247,46 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -322,6 +313,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -349,10 +341,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -486,7 +480,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -557,7 +550,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -569,7 +561,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -582,7 +573,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -606,7 +596,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -658,7 +647,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -701,7 +690,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -765,7 +754,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -819,7 +807,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -856,7 +843,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -894,7 +880,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -933,7 +918,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -942,22 +926,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -970,10 +996,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1008,7 +1033,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1032,7 +1056,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1042,7 +1065,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1055,18 +1077,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1079,10 +1097,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1116,7 +1133,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1140,7 +1156,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1151,13 +1166,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1171,21 +1184,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1239,7 +1249,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1286,7 +1295,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1299,7 +1307,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1314,7 +1321,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1342,7 +1348,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1376,7 +1381,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1438,7 +1442,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1491,7 +1494,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1547,7 +1549,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1582,7 +1583,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1596,7 +1596,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1633,7 +1632,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1671,7 +1669,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1681,29 +1678,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1779,7 +1773,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1820,7 +1814,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1842,7 +1835,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1899,7 +1891,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1962,7 +1953,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2001,7 +1991,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2038,7 +2027,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2053,7 +2041,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2079,7 +2066,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2102,7 +2088,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2129,20 +2114,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2170,7 +2152,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2195,7 +2177,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2228,7 +2209,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2256,7 +2236,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2281,7 +2260,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2306,7 +2284,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2335,13 +2312,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2359,6 +2334,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2367,7 +2343,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2394,13 +2370,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2424,14 +2398,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2456,13 +2430,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index dc05b96..aa7ee35 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,9 +3,10 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -45,7 +46,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -81,7 +81,6 @@ where + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -101,12 +100,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -118,7 +115,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -128,7 +126,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -139,7 +136,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -158,12 +154,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -193,7 +187,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -204,7 +197,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -225,12 +217,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -254,7 +244,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -278,7 +267,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/5b5196ad65db877c2f140dfc7a25f3fc6f2e40c6.patch b/patches/5b5196ad65db877c2f140dfc7a25f3fc6f2e40c6.patch new file mode 100644 index 0000000..769d898 --- /dev/null +++ b/patches/5b5196ad65db877c2f140dfc7a25f3fc6f2e40c6.patch @@ -0,0 +1,1797 @@ +diff --git a/buffered.rs b/buffered.rs +index ad567c9..a64f55b 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,13 +1,13 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, Initializer, DEFAULT_BUF_SIZE, Error, ErrorKind, SeekFrom, IoSlice, + IoSliceMut}; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -49,7 +49,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -73,7 +72,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -94,7 +92,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -129,7 +126,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { &self.inner } + + /// Gets a mutable reference to the underlying reader. +@@ -150,7 +146,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { &mut self.inner } + + /// Returns a reference to the internally buffered data. +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { self.inner } + + /// Invalidates all data in the internal buffer. +@@ -214,7 +207,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -234,7 +226,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -272,7 +263,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -292,7 +282,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader where R: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufReader") +@@ -302,7 +291,6 @@ impl fmt::Debug for BufReader where R: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -413,7 +401,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -448,7 +435,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -463,7 +449,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -481,7 +466,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { + inner: Some(inner), +@@ -530,7 +514,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.as_ref().unwrap() } + + /// Gets a mutable reference to the underlying writer. +@@ -548,7 +531,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.as_mut().unwrap() } + + /// Returns a reference to the internally buffered data. +@@ -564,7 +546,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -588,7 +569,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -597,7 +577,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -633,7 +612,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufWriter") +@@ -643,7 +621,6 @@ impl fmt::Debug for BufWriter where W: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -653,7 +630,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -692,7 +668,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { &self.1 } + + /// Returns the buffered writer instance which generated the error. +@@ -725,23 +700,13 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { self.0 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { iie.1 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -812,7 +777,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -833,7 +797,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -854,7 +817,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { + inner: BufWriter::with_capacity(capacity, inner), +@@ -878,7 +840,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.get_ref() } + + /// Gets a mutable reference to the underlying writer. +@@ -901,7 +862,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.get_mut() } + + /// Unwraps this `LineWriter`, returning the underlying writer. +@@ -927,7 +887,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { +@@ -938,7 +897,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -983,7 +941,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("LineWriter") +diff --git a/cursor.rs b/cursor.rs +index a94176e..7768d39 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Initializer, SeekFrom, Error, ErrorKind, IoSlice, IoSliceMut}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { self.inner } + + /// Gets a reference to the underlying value in this cursor. +@@ -128,7 +125,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { &self.inner } + + /// Gets a mutable reference to the underlying value in this cursor. +@@ -147,7 +143,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { &mut self.inner } + + /// Returns the current position of this cursor. +@@ -169,7 +164,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { self.pos } + + /// Sets the position of this cursor. +@@ -189,11 +183,9 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { self.pos = pos; } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor where T: AsRef<[u8]> { + fn seek(&mut self, style: SeekFrom) -> io::Result { + let (base_pos, offset) = match style { +@@ -222,10 +214,9 @@ impl io::Seek for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor where T: AsRef<[u8]> { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -244,7 +235,7 @@ impl Read for Cursor where T: AsRef<[u8]> { + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -255,12 +246,16 @@ impl Read for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor where T: AsRef<[u8]> { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++impl Cursor where T: AsRef<[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor where T: AsRef<[u8]> { ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { self.get_buf() } + fn consume(&mut self, amt: usize) { self.pos += amt as u64; } + } + +@@ -292,6 +287,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new(ErrorKind::InvalidInput, +@@ -318,6 +314,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -331,7 +328,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -347,7 +343,7 @@ impl Write for Cursor<&mut [u8]> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -361,7 +357,7 @@ impl Write for Cursor<&mut Vec> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -375,8 +371,8 @@ impl Write for Cursor> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index c29a68e..c94d8c5 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,13 @@ +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; +-use crate::convert::From; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++use core::convert::Into; ++use core::fmt; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++use core::result; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; ++use core::convert::From; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +43,6 @@ use crate::convert::From; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +56,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +69,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +90,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +130,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +142,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +156,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +186,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -245,14 +230,13 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error +- where E: Into> ++ where E: Into + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { + repr: Repr::Custom(Box::new(Custom { + kind, +@@ -261,24 +245,6 @@ impl Error { + } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -304,7 +270,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -335,7 +300,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -369,12 +333,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error+Send+Sync+'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -440,12 +403,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error+Send+Sync+'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -474,8 +436,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -501,10 +462,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -516,22 +476,18 @@ impl fmt::Debug for Repr { + match *self { + Repr::Os(code) => + fmt.debug_struct("Os") +- .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)).finish(), ++ .field("code", &code).finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), + } + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -539,33 +495,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index c959f2d..b645bc8 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,13 +1,15 @@ +-use crate::cmp; +-use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, BufRead, Error, ErrorKind, +- IoSliceMut, IoSlice}; +-use crate::fmt; +-use crate::mem; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++use core::cmp; ++use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, Error, ErrorKind, IoSliceMut, IoSlice}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::fmt; ++use core::mem; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -24,11 +26,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -39,7 +43,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -62,12 +65,11 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -86,7 +88,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -103,11 +105,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -118,7 +122,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -141,12 +145,12 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -186,7 +190,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -245,6 +248,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -254,7 +258,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(*self) } +@@ -268,7 +272,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -307,7 +310,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index be364a1..abbf09f 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,50 +257,38 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::slice; +-use crate::str; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(feature="collections")] use collections::string::String; ++use core::str; ++#[cfg(feature="collections")] use collections::vec::Vec; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::slice; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++ ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Result, Error, ErrorKind}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, sink, Sink, empty, Empty, repeat, Repeat}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stdin, stdout, stderr, Stdin, Stdout, Stderr}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StdoutLock, StderrLock, StdinLock}; +-#[unstable(feature = "print_internals", issue = "0")] +-pub use self::stdio::{_print, _eprint}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; + + pub mod prelude; +-mod buffered; ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + mod util; +-mod stdio; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { buf: &'a mut Vec, len: usize } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { self.buf.set_len(self.len); } +@@ -325,6 +313,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where F: FnOnce(&mut Vec) -> Result + { +@@ -352,10 +341,12 @@ fn append_to_string(buf: &mut String, f: F) -> Result + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -497,7 +488,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -565,7 +555,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -576,7 +565,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -603,7 +591,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -656,7 +643,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -699,7 +686,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -762,7 +749,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -814,7 +800,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + + /// Transforms this `Read` instance to an [`Iterator`] over its bytes. +@@ -851,7 +836,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes where Self: Sized { + Bytes { inner: self } + } +@@ -886,7 +870,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain where Self: Sized { + Chain { first: self, second: next, done_first: false } + } +@@ -922,22 +905,64 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take where Self: Sized { + Take { inner: self, limit: limit } + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -950,10 +975,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -989,7 +1013,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1013,7 +1036,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1023,7 +1045,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1036,11 +1057,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1053,10 +1072,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1091,7 +1109,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(mem::replace(&mut bufs, &mut []), 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1115,7 +1132,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1126,13 +1142,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1146,21 +1160,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1214,7 +1225,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1263,7 +1273,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1274,7 +1283,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1302,7 +1310,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1335,7 +1342,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1387,7 +1393,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1443,7 +1448,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + } + +@@ -1473,7 +1477,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1489,7 +1492,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1527,7 +1529,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1566,7 +1567,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1578,29 +1578,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + -> Result { + let mut read = 0; +@@ -1680,7 +1677,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1721,7 +1718,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1743,7 +1739,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1799,7 +1794,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1858,7 +1852,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1899,7 +1892,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split where Self: Sized { + Split { buf: self, delim: byte } + } +@@ -1938,7 +1930,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines where Self: Sized { + Lines { buf: self } + } +@@ -1950,7 +1941,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -1976,7 +1966,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -1999,7 +1988,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2026,13 +2014,11 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain") +@@ -2042,7 +2028,6 @@ impl fmt::Debug for Chain { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2074,7 +2059,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2101,7 +2086,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2136,7 +2120,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { self.limit } + + /// Sets the number of bytes that can be read before this instance will +@@ -2162,7 +2145,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2187,7 +2169,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2212,7 +2193,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2241,13 +2221,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2265,6 +2243,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2273,7 +2252,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2300,13 +2279,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2330,14 +2307,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2362,13 +2339,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 2e19edf..66294a3 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Write, Seek}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{Read, Write, BufRead, Seek}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index 33cc87e..75b8032 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, Read, Initializer, Write, ErrorKind, BufRead, IoSlice, IoSliceMut}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, Read, Initializer, Write, ErrorKind, IoSlice, IoSliceMut}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where R: Read, W: Write + { +@@ -70,7 +70,6 @@ pub fn copy(reader: &mut R, writer: &mut W) -> io::Result< + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { _priv: () } + + /// Constructs a new handle to an empty reader. +@@ -90,10 +89,8 @@ pub struct Empty { _priv: () } + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { Empty { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { Ok(0) } +@@ -103,7 +100,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(&[]) } +@@ -111,7 +109,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -124,7 +121,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { byte: u8 } + + /// Creates an instance of a reader that infinitely repeats one byte. +@@ -141,10 +137,8 @@ pub struct Repeat { byte: u8 } + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { Repeat { byte } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -169,7 +163,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -182,7 +175,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { _priv: () } + + /// Creates an instance of a writer which will successfully consume all data. +@@ -199,10 +191,8 @@ pub struct Sink { _priv: () } + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { Sink { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { Ok(buf.len()) } +@@ -217,7 +207,6 @@ impl Write for Sink { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/5d8fe1c4e6b214916de690ee25c17f862e166a28.patch b/patches/5d8fe1c4e6b214916de690ee25c17f862e166a28.patch new file mode 100644 index 0000000..4567509 --- /dev/null +++ b/patches/5d8fe1c4e6b214916de690ee25c17f862e166a28.patch @@ -0,0 +1,1888 @@ +diff --git a/buffered.rs b/buffered.rs +index 046b1a6..2ad53d6 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -222,7 +215,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -240,7 +232,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -260,7 +251,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -302,7 +292,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -322,7 +311,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -335,7 +323,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -446,7 +433,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -481,7 +467,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -496,7 +481,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -514,7 +498,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -561,7 +544,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -581,7 +563,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -599,7 +580,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -620,7 +600,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -644,7 +623,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -653,7 +631,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -693,7 +670,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -706,7 +682,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -716,7 +691,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -755,7 +729,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -790,28 +763,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -882,7 +844,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -903,7 +864,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -924,7 +884,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -945,7 +904,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -970,7 +928,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -998,7 +955,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -1006,7 +962,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1107,7 +1062,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index f3e3fc8..0e6fcdb 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -272,7 +263,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -283,15 +274,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -324,6 +324,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -352,6 +353,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -364,7 +366,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -387,7 +388,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -408,7 +409,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -429,8 +430,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index d80a388..8991308 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -432,12 +396,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -466,8 +429,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -493,10 +455,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -509,8 +470,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -518,13 +477,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -532,34 +489,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 01dff0b..eb78a0f 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -30,11 +34,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -45,7 +51,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -77,14 +82,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -107,7 +111,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -129,11 +133,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -144,7 +150,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -176,14 +182,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -227,7 +233,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -290,6 +295,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -299,7 +305,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -317,7 +323,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -363,7 +368,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 9cfb172..80c3318 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -258,54 +258,44 @@ + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + // ignore-tidy-filelength + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::mem; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++use core::mem; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -332,6 +322,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -359,10 +350,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -498,7 +491,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning + /// how many bytes were read. +@@ -565,7 +557,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -576,7 +567,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -589,7 +579,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -616,7 +605,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -669,7 +657,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -712,7 +700,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -775,7 +763,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -829,7 +816,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -871,7 +857,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -909,7 +894,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -948,7 +932,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -957,22 +940,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -985,10 +1010,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1023,7 +1047,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1047,7 +1070,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1057,7 +1079,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1070,18 +1091,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1094,10 +1111,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1131,7 +1147,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1155,7 +1170,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1166,13 +1180,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1186,21 +1198,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1254,7 +1263,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. + /// +@@ -1302,7 +1310,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1313,7 +1320,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1326,7 +1332,6 @@ pub trait Write { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1354,7 +1359,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1389,7 +1393,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1453,7 +1456,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + while !bufs.is_empty() { + match self.write_vectored(bufs) { +@@ -1506,7 +1508,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1562,7 +1563,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1597,7 +1597,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1613,7 +1612,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1651,7 +1649,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1690,7 +1687,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1702,29 +1698,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1803,7 +1796,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1844,7 +1837,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1866,7 +1858,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1922,7 +1913,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1981,7 +1971,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2022,7 +2011,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2064,7 +2052,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2079,7 +2066,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2105,7 +2091,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2128,7 +2113,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2155,20 +2139,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2196,7 +2177,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2221,7 +2202,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2256,7 +2236,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2284,7 +2263,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2309,7 +2287,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2334,7 +2311,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2363,13 +2339,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2387,6 +2361,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2395,7 +2370,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2422,13 +2397,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2452,14 +2425,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2484,13 +2457,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b9d5dc2..07d090e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -190,7 +184,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -203,7 +196,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -222,12 +214,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -251,7 +241,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/5d90154886039ddbd7c1b8bf4cc273b774b14ec7.patch b/patches/5d90154886039ddbd7c1b8bf4cc273b774b14ec7.patch new file mode 100644 index 0000000..5908559 --- /dev/null +++ b/patches/5d90154886039ddbd7c1b8bf4cc273b774b14ec7.patch @@ -0,0 +1,1850 @@ +diff --git a/buffered.rs b/buffered.rs +index 8862226..7898006 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -222,7 +215,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -240,7 +232,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -260,7 +251,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -298,7 +288,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -318,7 +307,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -331,7 +319,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -442,7 +429,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -477,7 +463,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -492,7 +477,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -510,7 +494,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -557,7 +540,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -577,7 +559,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -595,7 +576,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -616,7 +596,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -640,7 +619,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -649,7 +627,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -685,7 +662,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -698,7 +674,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -708,7 +683,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -747,7 +721,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -782,28 +755,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -874,7 +836,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -895,7 +856,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -916,7 +876,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -937,7 +896,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -962,7 +920,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -990,7 +947,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -998,7 +954,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1104,7 +1059,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index f36aa18..89d0701 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -268,7 +259,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -279,15 +270,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -320,6 +320,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -348,6 +349,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -360,7 +362,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -378,7 +379,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -394,7 +395,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -410,8 +411,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index 3b55d9b..c754d1f 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -432,12 +396,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -466,8 +429,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -493,10 +455,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -509,8 +470,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -518,13 +477,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -532,34 +489,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index b7f82e6..c857f83 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -25,11 +29,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -40,7 +46,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -67,14 +72,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -97,7 +101,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -114,11 +118,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -129,7 +135,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -156,14 +162,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -207,7 +213,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -265,6 +270,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -274,7 +280,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -292,7 +298,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -333,7 +338,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index dc83143..fc8896f 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,53 +257,43 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -330,6 +320,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -357,10 +348,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -496,7 +489,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning + /// how many bytes were read. +@@ -563,7 +555,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -574,7 +565,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -601,7 +591,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -654,7 +643,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -697,7 +686,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -760,7 +749,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -814,7 +802,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -856,7 +843,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -894,7 +880,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -933,7 +918,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -942,16 +926,60 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -964,10 +992,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1002,7 +1029,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1026,7 +1052,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1036,7 +1061,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1049,12 +1073,10 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1067,10 +1089,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1104,7 +1125,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1128,7 +1148,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1139,13 +1158,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1159,21 +1176,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1227,7 +1241,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. + /// +@@ -1275,7 +1288,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1286,7 +1298,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1314,7 +1325,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1349,7 +1359,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1402,7 +1411,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1458,7 +1466,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1493,7 +1500,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1509,7 +1515,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1547,7 +1552,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1586,7 +1590,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1598,29 +1601,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1699,7 +1699,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1740,7 +1740,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1762,7 +1761,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1818,7 +1816,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1877,7 +1874,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1918,7 +1914,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -1960,7 +1955,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -1975,7 +1969,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2001,7 +1994,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2024,7 +2016,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2051,20 +2042,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2092,7 +2080,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2117,7 +2105,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2152,7 +2139,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2180,7 +2166,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2205,7 +2190,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2230,7 +2214,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2259,13 +2242,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2283,6 +2264,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2291,7 +2273,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2318,13 +2300,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2348,14 +2328,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2380,13 +2360,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b09161b..e52119e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -185,7 +179,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -217,12 +209,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -241,7 +231,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/61150353bf9cc415f4554a9b4851c14e4255329f.patch b/patches/61150353bf9cc415f4554a9b4851c14e4255329f.patch new file mode 100644 index 0000000..5166a30 --- /dev/null +++ b/patches/61150353bf9cc415f4554a9b4851c14e4255329f.patch @@ -0,0 +1,1848 @@ +diff --git a/buffered.rs b/buffered.rs +index 8862226..7898006 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -222,7 +215,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -240,7 +232,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -260,7 +251,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -298,7 +288,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -318,7 +307,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -331,7 +319,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -442,7 +429,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -477,7 +463,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -492,7 +477,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -510,7 +494,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -557,7 +540,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -577,7 +559,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -595,7 +576,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -616,7 +596,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -640,7 +619,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -649,7 +627,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -685,7 +662,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -698,7 +674,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -708,7 +683,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -747,7 +721,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -782,28 +755,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -874,7 +836,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -895,7 +856,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -916,7 +876,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -937,7 +896,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -962,7 +920,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -990,7 +947,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -998,7 +954,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1104,7 +1059,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index f36aa18..89d0701 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -268,7 +259,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -279,15 +270,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -320,6 +320,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -348,6 +349,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -360,7 +362,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -378,7 +379,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -394,7 +395,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -410,8 +411,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index 3b55d9b..c754d1f 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -432,12 +396,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -466,8 +429,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -493,10 +455,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -509,8 +470,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -518,13 +477,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -532,34 +489,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index b7f82e6..c857f83 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -25,11 +29,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -40,7 +46,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -67,14 +72,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -97,7 +101,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -114,11 +118,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -129,7 +135,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -156,14 +162,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -207,7 +213,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -265,6 +270,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -274,7 +280,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -292,7 +298,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -333,7 +338,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 420d6ea..c8613a1 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,53 +257,43 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -330,6 +320,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -357,10 +348,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -496,7 +489,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning + /// how many bytes were read. +@@ -563,7 +555,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -574,7 +565,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -601,7 +591,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -654,7 +643,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -697,7 +686,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -760,7 +749,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -814,7 +802,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -856,7 +843,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -894,7 +880,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -933,7 +918,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -942,16 +926,59 @@ pub trait Read { + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -964,10 +991,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1002,7 +1028,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1026,7 +1051,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1036,7 +1060,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1049,11 +1072,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1066,10 +1087,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1103,7 +1123,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1127,7 +1146,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1138,13 +1156,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1158,21 +1174,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1226,7 +1239,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. + /// +@@ -1274,7 +1286,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1285,7 +1296,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1313,7 +1323,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1348,7 +1357,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1401,7 +1409,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1457,7 +1464,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1492,7 +1498,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1508,7 +1513,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1546,7 +1550,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1585,7 +1588,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1597,29 +1599,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1698,7 +1697,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1739,7 +1738,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1761,7 +1759,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1817,7 +1814,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1876,7 +1872,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1917,7 +1912,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -1959,7 +1953,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -1974,7 +1967,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2000,7 +1992,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2023,7 +2014,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2050,20 +2040,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2091,7 +2078,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2116,7 +2103,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2151,7 +2137,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2179,7 +2164,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2204,7 +2188,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2229,7 +2212,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2258,13 +2240,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2282,6 +2262,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2290,7 +2271,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2317,13 +2298,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2347,14 +2326,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2379,13 +2358,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b09161b..e52119e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -185,7 +179,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -217,12 +209,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -241,7 +231,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/6276c135d185e8492e8a2b9db5ca04e51c3293fa.patch b/patches/6276c135d185e8492e8a2b9db5ca04e51c3293fa.patch new file mode 100644 index 0000000..f697a4d --- /dev/null +++ b/patches/6276c135d185e8492e8a2b9db5ca04e51c3293fa.patch @@ -0,0 +1,1893 @@ +diff --git a/buffered.rs b/buffered.rs +index 0737008..e5adb4b 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -197,7 +191,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -221,7 +214,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -239,7 +231,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -259,7 +250,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -301,7 +291,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -321,7 +310,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -334,7 +322,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -445,7 +432,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -480,7 +466,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -495,7 +480,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -513,7 +497,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -560,7 +543,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -580,7 +562,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -598,7 +579,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -618,7 +598,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -642,7 +621,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -651,7 +629,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -691,7 +668,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -704,7 +680,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -714,7 +689,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -753,7 +727,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -788,28 +761,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -880,7 +842,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -901,7 +862,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -922,7 +882,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -943,7 +902,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -968,7 +926,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -996,7 +953,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -1004,7 +960,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1105,7 +1060,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index f4db5f8..4f20b8a 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -272,7 +263,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -283,15 +274,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -324,6 +324,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -352,6 +353,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -364,7 +366,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -387,7 +388,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -408,7 +409,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -429,8 +430,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index f7248e7..f7311ad 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,12 +143,10 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -165,7 +154,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -174,7 +162,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -205,7 +192,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -248,36 +234,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -303,7 +270,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -334,7 +300,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -368,12 +333,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -437,12 +401,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -471,8 +434,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -498,10 +460,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -514,8 +475,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -523,13 +482,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -537,34 +494,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 01dff0b..eb78a0f 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -30,11 +34,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -45,7 +51,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -77,14 +82,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -107,7 +111,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -129,11 +133,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -144,7 +150,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -176,14 +182,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -227,7 +233,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -290,6 +295,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -299,7 +305,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -317,7 +323,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -363,7 +368,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 717d286..8a46366 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -258,54 +258,44 @@ + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + // ignore-tidy-filelength + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::mem; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++use core::mem; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -332,6 +322,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -359,10 +350,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -498,7 +491,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning + /// how many bytes were read. +@@ -570,7 +562,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -582,7 +573,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -595,7 +585,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -622,7 +611,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -675,7 +663,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -718,7 +706,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -781,7 +769,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -835,7 +822,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -877,7 +863,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -915,7 +900,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -954,7 +938,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -963,22 +946,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -991,10 +1016,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1029,7 +1053,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1053,7 +1076,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1063,7 +1085,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1076,18 +1097,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1100,10 +1117,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1137,7 +1153,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1161,7 +1176,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1172,13 +1186,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1192,21 +1204,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1260,7 +1269,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. + /// +@@ -1308,7 +1316,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1319,7 +1326,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1332,7 +1338,6 @@ pub trait Write { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1360,7 +1365,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1395,7 +1399,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1459,7 +1462,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + while !bufs.is_empty() { + match self.write_vectored(bufs) { +@@ -1512,7 +1514,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1568,7 +1569,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1603,7 +1603,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1619,7 +1618,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1657,7 +1655,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1696,7 +1693,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1708,29 +1704,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1809,7 +1802,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1850,7 +1843,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1872,7 +1864,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1932,7 +1923,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1995,7 +1985,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2036,7 +2025,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2078,7 +2066,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2093,7 +2080,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2119,7 +2105,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2142,7 +2127,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2169,20 +2153,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2210,7 +2191,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2235,7 +2216,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2270,7 +2250,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2298,7 +2277,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2323,7 +2301,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2348,7 +2325,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2377,13 +2353,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2401,6 +2375,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2409,7 +2384,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2436,13 +2411,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2466,14 +2439,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2498,13 +2471,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b9d5dc2..07d090e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -190,7 +184,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -203,7 +196,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -222,12 +214,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -251,7 +241,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/62e86b42b5ed342d30c539e22810c26d312995e2.patch b/patches/62e86b42b5ed342d30c539e22810c26d312995e2.patch new file mode 100644 index 0000000..f47813c --- /dev/null +++ b/patches/62e86b42b5ed342d30c539e22810c26d312995e2.patch @@ -0,0 +1,1797 @@ +diff --git a/buffered.rs b/buffered.rs +index 9593a1b..0b6c3eb 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,13 +1,13 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, Initializer, DEFAULT_BUF_SIZE, Error, ErrorKind, SeekFrom, IoSlice, + IoSliceMut}; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -47,7 +47,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -71,7 +70,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -92,7 +90,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -127,7 +124,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { &self.inner } + + /// Gets a mutable reference to the underlying reader. +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { &mut self.inner } + + /// Returns a reference to the internally buffered data. +@@ -172,7 +167,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -195,7 +189,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { self.inner } + + /// Invalidates all data in the internal buffer. +@@ -211,7 +204,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -231,7 +223,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -269,7 +260,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -289,7 +279,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader where R: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufReader") +@@ -299,7 +288,6 @@ impl fmt::Debug for BufReader where R: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -410,7 +398,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -445,7 +432,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -460,7 +446,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -478,7 +463,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { + inner: Some(inner), +@@ -527,7 +511,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.as_ref().unwrap() } + + /// Gets a mutable reference to the underlying writer. +@@ -545,7 +528,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.as_mut().unwrap() } + + /// Returns a reference to the internally buffered data. +@@ -561,7 +543,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -585,7 +566,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -594,7 +574,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -630,7 +609,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufWriter") +@@ -640,7 +618,6 @@ impl fmt::Debug for BufWriter where W: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -650,7 +627,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -689,7 +665,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { &self.1 } + + /// Returns the buffered writer instance which generated the error. +@@ -722,23 +697,13 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { self.0 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { iie.1 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -809,7 +774,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -830,7 +794,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -851,7 +814,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { + inner: BufWriter::with_capacity(capacity, inner), +@@ -875,7 +837,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.get_ref() } + + /// Gets a mutable reference to the underlying writer. +@@ -898,7 +859,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.get_mut() } + + /// Unwraps this `LineWriter`, returning the underlying writer. +@@ -924,7 +884,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { +@@ -935,7 +894,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -980,7 +938,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("LineWriter") +diff --git a/cursor.rs b/cursor.rs +index a94176e..7768d39 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Initializer, SeekFrom, Error, ErrorKind, IoSlice, IoSliceMut}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { self.inner } + + /// Gets a reference to the underlying value in this cursor. +@@ -128,7 +125,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { &self.inner } + + /// Gets a mutable reference to the underlying value in this cursor. +@@ -147,7 +143,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { &mut self.inner } + + /// Returns the current position of this cursor. +@@ -169,7 +164,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { self.pos } + + /// Sets the position of this cursor. +@@ -189,11 +183,9 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { self.pos = pos; } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor where T: AsRef<[u8]> { + fn seek(&mut self, style: SeekFrom) -> io::Result { + let (base_pos, offset) = match style { +@@ -222,10 +214,9 @@ impl io::Seek for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor where T: AsRef<[u8]> { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -244,7 +235,7 @@ impl Read for Cursor where T: AsRef<[u8]> { + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -255,12 +246,16 @@ impl Read for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor where T: AsRef<[u8]> { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++impl Cursor where T: AsRef<[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor where T: AsRef<[u8]> { ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { self.get_buf() } + fn consume(&mut self, amt: usize) { self.pos += amt as u64; } + } + +@@ -292,6 +287,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new(ErrorKind::InvalidInput, +@@ -318,6 +314,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -331,7 +328,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -347,7 +343,7 @@ impl Write for Cursor<&mut [u8]> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -361,7 +357,7 @@ impl Write for Cursor<&mut Vec> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -375,8 +371,8 @@ impl Write for Cursor> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index c29a68e..c94d8c5 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,13 @@ +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; +-use crate::convert::From; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++use core::convert::Into; ++use core::fmt; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++use core::result; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; ++use core::convert::From; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +43,6 @@ use crate::convert::From; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +56,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +69,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +90,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +130,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +142,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +156,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +186,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -245,14 +230,13 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error +- where E: Into> ++ where E: Into + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { + repr: Repr::Custom(Box::new(Custom { + kind, +@@ -261,24 +245,6 @@ impl Error { + } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -304,7 +270,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -335,7 +300,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -369,12 +333,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error+Send+Sync+'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -440,12 +403,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error+Send+Sync+'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -474,8 +436,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -501,10 +462,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -516,22 +476,18 @@ impl fmt::Debug for Repr { + match *self { + Repr::Os(code) => + fmt.debug_struct("Os") +- .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)).finish(), ++ .field("code", &code).finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), + } + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -539,33 +495,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index c959f2d..b645bc8 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,13 +1,15 @@ +-use crate::cmp; +-use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, BufRead, Error, ErrorKind, +- IoSliceMut, IoSlice}; +-use crate::fmt; +-use crate::mem; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++use core::cmp; ++use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, Error, ErrorKind, IoSliceMut, IoSlice}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::fmt; ++use core::mem; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -24,11 +26,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -39,7 +43,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -62,12 +65,11 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -86,7 +88,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -103,11 +105,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -118,7 +122,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -141,12 +145,12 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -186,7 +190,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -245,6 +248,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -254,7 +258,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(*self) } +@@ -268,7 +272,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -307,7 +310,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index be364a1..abbf09f 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,50 +257,38 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::slice; +-use crate::str; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(feature="collections")] use collections::string::String; ++use core::str; ++#[cfg(feature="collections")] use collections::vec::Vec; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::slice; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++ ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Result, Error, ErrorKind}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, sink, Sink, empty, Empty, repeat, Repeat}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stdin, stdout, stderr, Stdin, Stdout, Stderr}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StdoutLock, StderrLock, StdinLock}; +-#[unstable(feature = "print_internals", issue = "0")] +-pub use self::stdio::{_print, _eprint}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; + + pub mod prelude; +-mod buffered; ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + mod util; +-mod stdio; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { buf: &'a mut Vec, len: usize } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { self.buf.set_len(self.len); } +@@ -325,6 +313,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where F: FnOnce(&mut Vec) -> Result + { +@@ -352,10 +341,12 @@ fn append_to_string(buf: &mut String, f: F) -> Result + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -497,7 +488,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -565,7 +555,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -576,7 +565,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -603,7 +591,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -656,7 +643,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -699,7 +686,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -762,7 +749,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -814,7 +800,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + + /// Transforms this `Read` instance to an [`Iterator`] over its bytes. +@@ -851,7 +836,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes where Self: Sized { + Bytes { inner: self } + } +@@ -886,7 +870,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain where Self: Sized { + Chain { first: self, second: next, done_first: false } + } +@@ -922,22 +905,64 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take where Self: Sized { + Take { inner: self, limit: limit } + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -950,10 +975,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -989,7 +1013,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1013,7 +1036,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1023,7 +1045,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1036,11 +1057,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1053,10 +1072,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1091,7 +1109,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(mem::replace(&mut bufs, &mut []), 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1115,7 +1132,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1126,13 +1142,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1146,21 +1160,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1214,7 +1225,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1263,7 +1273,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1274,7 +1283,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1302,7 +1310,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1335,7 +1342,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1387,7 +1393,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1443,7 +1448,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + } + +@@ -1473,7 +1477,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1489,7 +1492,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1527,7 +1529,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1566,7 +1567,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1578,29 +1578,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + -> Result { + let mut read = 0; +@@ -1680,7 +1677,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1721,7 +1718,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1743,7 +1739,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1799,7 +1794,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1858,7 +1852,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1899,7 +1892,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split where Self: Sized { + Split { buf: self, delim: byte } + } +@@ -1938,7 +1930,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines where Self: Sized { + Lines { buf: self } + } +@@ -1950,7 +1941,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -1976,7 +1966,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -1999,7 +1988,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2026,13 +2014,11 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain") +@@ -2042,7 +2028,6 @@ impl fmt::Debug for Chain { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2074,7 +2059,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2101,7 +2086,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2136,7 +2120,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { self.limit } + + /// Sets the number of bytes that can be read before this instance will +@@ -2162,7 +2145,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2187,7 +2169,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2212,7 +2193,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2241,13 +2221,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2265,6 +2243,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2273,7 +2252,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2300,13 +2279,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2330,14 +2307,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2362,13 +2339,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 2e19edf..66294a3 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Write, Seek}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{Read, Write, BufRead, Seek}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index 33cc87e..75b8032 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, Read, Initializer, Write, ErrorKind, BufRead, IoSlice, IoSliceMut}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, Read, Initializer, Write, ErrorKind, IoSlice, IoSliceMut}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where R: Read, W: Write + { +@@ -70,7 +70,6 @@ pub fn copy(reader: &mut R, writer: &mut W) -> io::Result< + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { _priv: () } + + /// Constructs a new handle to an empty reader. +@@ -90,10 +89,8 @@ pub struct Empty { _priv: () } + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { Empty { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { Ok(0) } +@@ -103,7 +100,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(&[]) } +@@ -111,7 +109,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -124,7 +121,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { byte: u8 } + + /// Creates an instance of a reader that infinitely repeats one byte. +@@ -141,10 +137,8 @@ pub struct Repeat { byte: u8 } + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { Repeat { byte } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -169,7 +163,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -182,7 +175,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { _priv: () } + + /// Creates an instance of a writer which will successfully consume all data. +@@ -199,10 +191,8 @@ pub struct Sink { _priv: () } + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { Sink { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { Ok(buf.len()) } +@@ -217,7 +207,6 @@ impl Write for Sink { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/65bdf79da3f72269e6fe7aac1355df1420613889.patch b/patches/65bdf79da3f72269e6fe7aac1355df1420613889.patch new file mode 100644 index 0000000..153c7fa --- /dev/null +++ b/patches/65bdf79da3f72269e6fe7aac1355df1420613889.patch @@ -0,0 +1,1911 @@ +diff --git a/buffered.rs b/buffered.rs +index 97c4b87..ae26453 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -3,15 +3,15 @@ + #[cfg(test)] + mod tests; + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -52,7 +52,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -76,7 +75,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -97,7 +95,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -127,7 +124,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -150,7 +146,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -178,7 +173,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -201,7 +195,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -225,7 +218,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -243,7 +235,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -263,7 +254,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -305,7 +295,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -325,7 +314,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -338,7 +326,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -492,7 +479,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: Write::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: Write::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -527,7 +513,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -542,7 +527,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -560,7 +544,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -655,7 +638,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -675,7 +657,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -693,7 +674,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -713,7 +693,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -737,7 +716,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -746,7 +724,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -810,7 +787,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -823,7 +799,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -834,7 +809,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -874,7 +848,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -909,28 +882,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -1267,7 +1229,6 @@ impl<'a, W: Write> Write for LineWriterShim<'a, W> { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -1287,7 +1248,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -1308,7 +1268,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -1329,7 +1288,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -1354,7 +1312,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -1382,7 +1339,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner + .into_inner() +@@ -1390,7 +1346,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -1421,7 +1376,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index 5733735..0fdd84a 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,7 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -111,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -129,7 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -150,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -196,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -242,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -271,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -282,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -323,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -351,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -363,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -386,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -407,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -428,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index e09e7ba..126a710 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -230,7 +236,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -293,6 +298,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -302,7 +308,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -320,7 +326,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -366,7 +371,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index adea8a8..e647c6b 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -247,56 +247,46 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -323,6 +313,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -350,10 +341,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -487,7 +480,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -558,7 +550,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -570,7 +561,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -583,7 +573,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -607,7 +596,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -659,7 +647,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -702,7 +690,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -766,7 +754,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -820,7 +807,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -857,7 +843,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -895,7 +880,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -934,7 +918,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -943,22 +926,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -971,10 +996,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1009,7 +1033,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1033,7 +1056,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1043,7 +1065,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1056,18 +1077,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1080,10 +1097,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1117,7 +1133,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1141,7 +1156,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1152,13 +1166,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1172,21 +1184,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1240,7 +1249,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1287,7 +1295,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1300,7 +1307,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1315,7 +1321,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1343,7 +1348,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1377,7 +1381,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1439,7 +1442,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1492,7 +1494,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1548,7 +1549,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1583,7 +1583,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1597,7 +1596,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1634,7 +1632,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1672,7 +1669,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1682,29 +1678,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1780,7 +1773,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1821,7 +1814,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1843,7 +1835,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1900,7 +1891,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1963,7 +1953,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2002,7 +1991,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2039,7 +2027,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2054,7 +2041,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2080,7 +2066,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2103,7 +2088,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2130,20 +2114,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2171,7 +2152,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2196,7 +2177,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2229,7 +2209,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2257,7 +2236,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2282,7 +2260,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2307,7 +2284,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2336,13 +2312,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2360,6 +2334,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2368,7 +2343,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2395,13 +2370,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2425,14 +2398,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2457,13 +2430,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index dc05b96..aa7ee35 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,9 +3,10 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -45,7 +46,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -81,7 +81,6 @@ where + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -101,12 +100,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -118,7 +115,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -128,7 +126,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -139,7 +136,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -158,12 +154,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -193,7 +187,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -204,7 +197,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -225,12 +217,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -254,7 +244,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -278,7 +267,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/68f2934a154abac9a2af72c55e4c08277172e087.patch b/patches/68f2934a154abac9a2af72c55e4c08277172e087.patch new file mode 100644 index 0000000..418a383 --- /dev/null +++ b/patches/68f2934a154abac9a2af72c55e4c08277172e087.patch @@ -0,0 +1,2082 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 02b0fc0..fe6e4af 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,8 +1,9 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, SizeHint, DEFAULT_BUF_SIZE, + }; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -44,7 +45,6 @@ use crate::io::{ + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -68,7 +68,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -89,7 +88,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buf = Box::new_uninit_slice(capacity).assume_init(); +@@ -118,7 +116,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -141,7 +138,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -169,7 +165,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -192,7 +187,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -216,7 +210,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -234,7 +227,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -254,7 +246,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -310,7 +301,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -330,7 +320,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -343,7 +332,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index 65bc2fc..46cd6b8 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,9 +1,9 @@ +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; +-use crate::mem; ++use core::mem; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -65,7 +65,6 @@ use crate::mem; + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -87,7 +86,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -105,7 +103,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -200,7 +197,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -220,7 +216,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -238,7 +233,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -270,7 +264,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -294,7 +287,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -325,7 +317,6 @@ impl BufWriter { + /// assert_eq!(recovered_writer.len(), 0); + /// assert_eq!(&buffered_data.unwrap(), b"ata"); + /// ``` +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_raw_parts(mut self) -> (W, Result, WriterPanicked>) { + let buf = mem::take(&mut self.buf); + let buf = if !self.panicked { Ok(buf) } else { Err(WriterPanicked { buf }) }; +@@ -333,7 +324,6 @@ impl BufWriter { + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + /// Error returned for the buffered data from `BufWriter::into_raw_parts`, when the underlying + /// writer has previously panicked. Contains the (possibly partly written) buffered data. + /// +@@ -367,7 +357,6 @@ pub struct WriterPanicked { + impl WriterPanicked { + /// Returns the perhaps-unwritten data. Some of this data may have been written by the + /// panicking call(s) to the underlying writer, so simply writing it again is not a good idea. +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_inner(self) -> Vec { + self.buf + } +@@ -376,22 +365,12 @@ impl WriterPanicked { + "BufWriter inner writer panicked, what data remains unwritten is not known"; + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] +-impl error::Error for WriterPanicked { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- Self::DESCRIPTION +- } +-} +- +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Display for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + write!(f, "{}", Self::DESCRIPTION) + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Debug for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("WriterPanicked") +@@ -400,7 +379,6 @@ impl fmt::Debug for WriterPanicked { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -497,7 +475,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -510,7 +487,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -521,7 +497,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index d0c859d..a052adf 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index 6549781..0dc7440 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,7 +119,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } +@@ -143,7 +139,6 @@ impl IntoInnerError { + /// let err = into_inner_err.into_error(); + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_error(self) -> Error { + self.1 + } +@@ -167,28 +162,17 @@ impl IntoInnerError { + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// assert_eq!(recovered_writer.buffer(), b"t be actually written"); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_parts(self) -> (Error, W) { + (self.1, self.0) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/copy.rs b/copy.rs +index eb60df2..df99a47 100644 +--- a/copy.rs ++++ b/copy.rs +@@ -1,5 +1,6 @@ +-use super::{BufWriter, ErrorKind, Read, Result, Write, DEFAULT_BUF_SIZE}; +-use crate::mem::MaybeUninit; ++use super::{ErrorKind, Read, Result, Write, DEFAULT_BUF_SIZE}; ++#[cfg(feature = "collections")] use super::BufWriter; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,19 +40,12 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> Result + where + R: Read, + W: Write, + { +- cfg_if::cfg_if! { +- if #[cfg(any(target_os = "linux", target_os = "android"))] { +- crate::sys::kernel_copy::copy_spec(reader, writer) +- } else { +- generic_copy(reader, writer) +- } +- } ++ generic_copy(reader, writer) + } + + /// The userspace read-write-loop implementation of `io::copy` that is used when +@@ -76,6 +70,7 @@ impl BufferedCopySpec for W { + } + } + ++#[cfg(feature = "collections")] + impl BufferedCopySpec for BufWriter { + fn copy_to(reader: &mut R, writer: &mut Self) -> Result { + if writer.capacity() < DEFAULT_BUF_SIZE { +diff --git a/cursor.rs b/cursor.rs +index bbee2cc..dc75216 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,8 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,8 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn get_ref(&self) -> &T { + &self.inner + } +@@ -152,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -176,8 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn position(&self) -> u64 { + self.pos + } +@@ -199,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -245,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -274,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -285,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -326,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -354,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -366,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -389,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -410,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -431,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 00bf8b9..5c0e7cd 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -216,7 +222,6 @@ impl BufRead for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -279,6 +284,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -288,7 +294,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -310,7 +316,6 @@ impl BufRead for &[u8] { + /// If the number of bytes to be written exceeds the size of the slice, write operations will + /// return short writes: ultimately, `Ok(0)`; in this situation, `write_all` returns an error of + /// kind `ErrorKind::WriteZero`. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -356,7 +361,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 17002e3..dde604d 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -246,58 +246,48 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::copy::copy; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[unstable(feature = "internal_output_capture", issue = "none")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::set_output_capture; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + pub(crate) mod copy; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -324,6 +314,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -351,10 +342,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -504,7 +497,6 @@ pub(crate) fn default_read_exact(this: &mut R, mut buf: &mut [ + /// [`&str`]: prim@str + /// [`std::io`]: self + /// [`File`]: crate::fs::File +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -575,7 +567,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -587,7 +578,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -600,7 +590,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -624,7 +613,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -676,7 +664,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -719,7 +707,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -783,7 +771,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, buf: &mut [u8]) -> Result<()> { + default_read_exact(self, buf) + } +@@ -822,7 +809,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -859,7 +845,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -897,7 +882,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -936,7 +920,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -986,29 +969,71 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +-#[unstable(feature = "io_read_to_string", issue = "80218")] ++#[cfg(feature="collections")] + pub fn read_to_string(reader: &mut R) -> Result { + let mut buf = String::new(); + reader.read_to_string(&mut buf)?; + Ok(buf) + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1021,10 +1046,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1059,7 +1083,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1083,7 +1106,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1093,7 +1115,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1106,18 +1127,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1130,10 +1147,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1167,7 +1183,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1191,7 +1206,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1202,13 +1216,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1222,21 +1234,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1290,7 +1299,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1337,7 +1345,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1350,7 +1357,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1365,7 +1371,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1393,7 +1398,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1427,7 +1431,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1489,7 +1492,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1542,7 +1544,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1598,7 +1599,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1633,7 +1633,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1647,7 +1646,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1684,7 +1682,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_stream_len", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1721,7 +1718,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "seek_convenience", since = "1.51.0")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1731,29 +1727,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1829,7 +1822,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1870,7 +1863,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1892,7 +1884,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1949,7 +1940,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -2012,7 +2002,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2050,7 +2039,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2087,7 +2075,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2102,7 +2089,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2128,7 +2114,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2151,7 +2136,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2178,20 +2162,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2219,7 +2200,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2257,7 +2238,6 @@ impl SizeHint for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2290,7 +2270,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2318,7 +2297,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2343,7 +2321,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2368,7 +2345,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2397,13 +2373,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2421,6 +2395,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2429,7 +2404,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2456,13 +2431,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2510,14 +2483,14 @@ impl SizeHint for T { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2542,13 +2515,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index d806431..6b9791a 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index f472361..0a1899d 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,16 +3,16 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; ++use core::fmt; + use crate::io::{ +- self, BufRead, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, SizeHint, Write, ++ self, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, SizeHint, Write, + }; ++#[cfg(feature="collections")] use crate::io::BufRead; + + /// A reader which is always at EOF. + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -32,13 +32,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -50,7 +47,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -60,7 +58,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "empty_seek", since = "1.51.0")] + impl Seek for Empty { + fn seek(&mut self, _pos: SeekFrom) -> io::Result { + Ok(0) +@@ -75,7 +72,6 @@ impl Seek for Empty { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -92,7 +88,6 @@ impl SizeHint for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -111,13 +106,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -147,7 +139,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -158,7 +149,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -179,13 +169,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -209,7 +196,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -233,7 +219,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/6f4681bacc78a00a63766f12a17560701ab5c1e8.patch b/patches/6f4681bacc78a00a63766f12a17560701ab5c1e8.patch new file mode 100644 index 0000000..9133212 --- /dev/null +++ b/patches/6f4681bacc78a00a63766f12a17560701ab5c1e8.patch @@ -0,0 +1,1891 @@ +diff --git a/buffered.rs b/buffered.rs +index f3aadf2..3826382 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -49,7 +49,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -73,7 +72,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -94,7 +92,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -124,7 +121,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -147,7 +143,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -222,7 +215,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -240,7 +232,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -260,7 +251,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -302,7 +292,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -322,7 +311,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -335,7 +323,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -444,7 +431,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: Write::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: Write::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -479,7 +465,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -494,7 +479,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -512,7 +496,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -559,7 +542,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -579,7 +561,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -597,7 +578,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -617,7 +597,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -641,7 +620,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -650,7 +628,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -690,7 +667,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -703,7 +679,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -713,7 +688,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -753,7 +727,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -788,28 +761,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -878,7 +840,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -899,7 +860,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -920,7 +880,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -941,7 +900,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -966,7 +924,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -994,7 +951,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -1002,7 +958,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1103,7 +1058,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index 58343f6..6750136 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -67,7 +67,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -90,7 +89,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -108,7 +106,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -126,7 +123,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -147,7 +143,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -171,7 +166,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -193,13 +187,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -239,13 +231,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -268,7 +259,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -279,15 +270,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -320,6 +320,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -348,6 +349,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -360,7 +362,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -383,7 +384,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -404,7 +405,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -425,8 +426,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index e6eda2c..be46887 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -51,12 +56,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -66,13 +69,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -84,48 +90,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -137,10 +130,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -151,12 +142,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -164,7 +153,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -173,7 +161,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -204,7 +191,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -244,36 +230,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -299,7 +266,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -333,7 +299,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -369,12 +334,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -440,12 +404,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -476,8 +439,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -503,10 +465,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -519,8 +480,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -528,13 +487,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -542,34 +499,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 01dff0b..eb78a0f 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -30,11 +34,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -45,7 +51,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -77,14 +82,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -107,7 +111,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -129,11 +133,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -144,7 +150,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -176,14 +182,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -227,7 +233,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -290,6 +295,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -299,7 +305,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -317,7 +323,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -363,7 +368,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 462b696..e3dd32a 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -247,53 +247,43 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -320,6 +310,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -347,10 +338,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -484,7 +477,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -555,7 +547,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -567,7 +558,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -580,7 +570,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -604,7 +593,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -656,7 +644,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -699,7 +687,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -763,7 +751,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -817,7 +804,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -854,7 +840,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -892,7 +877,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -931,7 +915,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -940,22 +923,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -968,10 +993,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1006,7 +1030,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1030,7 +1053,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1040,7 +1062,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1053,18 +1074,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1077,10 +1094,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1114,7 +1130,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1138,7 +1153,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1149,13 +1163,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1169,21 +1181,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1237,7 +1246,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1284,7 +1292,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1297,7 +1304,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1312,7 +1318,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1340,7 +1345,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1374,7 +1378,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1436,7 +1439,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1489,7 +1491,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1545,7 +1546,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1580,7 +1580,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1594,7 +1593,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1631,7 +1629,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1669,7 +1666,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1679,29 +1675,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1777,7 +1770,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1818,7 +1811,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1840,7 +1832,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1897,7 +1888,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1960,7 +1950,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1999,7 +1988,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2036,7 +2024,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2051,7 +2038,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2077,7 +2063,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2100,7 +2085,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2127,20 +2111,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2168,7 +2149,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2193,7 +2174,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2226,7 +2206,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2254,7 +2233,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2279,7 +2257,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2304,7 +2281,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2333,13 +2309,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2357,6 +2331,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2365,7 +2340,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2392,13 +2367,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2422,14 +2395,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2454,13 +2427,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index a093b74..1e468ae 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -42,7 +43,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -75,7 +75,6 @@ where + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -95,12 +94,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -112,7 +109,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -122,7 +120,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -133,7 +130,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -152,12 +148,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -187,7 +181,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -219,12 +211,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -248,7 +238,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/73c3a496cc8ce261e87abbd998b36ab16dab4f4b.patch b/patches/73c3a496cc8ce261e87abbd998b36ab16dab4f4b.patch new file mode 100644 index 0000000..5908559 --- /dev/null +++ b/patches/73c3a496cc8ce261e87abbd998b36ab16dab4f4b.patch @@ -0,0 +1,1850 @@ +diff --git a/buffered.rs b/buffered.rs +index 8862226..7898006 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -222,7 +215,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -240,7 +232,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -260,7 +251,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -298,7 +288,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -318,7 +307,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -331,7 +319,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -442,7 +429,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -477,7 +463,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -492,7 +477,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -510,7 +494,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -557,7 +540,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -577,7 +559,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -595,7 +576,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -616,7 +596,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -640,7 +619,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -649,7 +627,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -685,7 +662,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -698,7 +674,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -708,7 +683,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -747,7 +721,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -782,28 +755,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -874,7 +836,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -895,7 +856,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -916,7 +876,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -937,7 +896,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -962,7 +920,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -990,7 +947,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -998,7 +954,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1104,7 +1059,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index f36aa18..89d0701 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -268,7 +259,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -279,15 +270,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -320,6 +320,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -348,6 +349,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -360,7 +362,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -378,7 +379,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -394,7 +395,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -410,8 +411,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index 3b55d9b..c754d1f 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -432,12 +396,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -466,8 +429,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -493,10 +455,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -509,8 +470,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -518,13 +477,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -532,34 +489,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index b7f82e6..c857f83 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -25,11 +29,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -40,7 +46,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -67,14 +72,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -97,7 +101,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -114,11 +118,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -129,7 +135,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -156,14 +162,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -207,7 +213,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -265,6 +270,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -274,7 +280,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -292,7 +298,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -333,7 +338,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index dc83143..fc8896f 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,53 +257,43 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -330,6 +320,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -357,10 +348,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -496,7 +489,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning + /// how many bytes were read. +@@ -563,7 +555,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -574,7 +565,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -601,7 +591,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -654,7 +643,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -697,7 +686,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -760,7 +749,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -814,7 +802,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -856,7 +843,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -894,7 +880,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -933,7 +918,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -942,16 +926,60 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -964,10 +992,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1002,7 +1029,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1026,7 +1052,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1036,7 +1061,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1049,12 +1073,10 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1067,10 +1089,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1104,7 +1125,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1128,7 +1148,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1139,13 +1158,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1159,21 +1176,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1227,7 +1241,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. + /// +@@ -1275,7 +1288,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1286,7 +1298,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1314,7 +1325,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1349,7 +1359,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1402,7 +1411,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1458,7 +1466,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1493,7 +1500,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1509,7 +1515,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1547,7 +1552,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1586,7 +1590,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1598,29 +1601,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1699,7 +1699,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1740,7 +1740,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1762,7 +1761,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1818,7 +1816,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1877,7 +1874,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1918,7 +1914,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -1960,7 +1955,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -1975,7 +1969,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2001,7 +1994,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2024,7 +2016,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2051,20 +2042,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2092,7 +2080,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2117,7 +2105,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2152,7 +2139,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2180,7 +2166,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2205,7 +2190,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2230,7 +2214,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2259,13 +2242,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2283,6 +2264,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2291,7 +2273,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2318,13 +2300,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2348,14 +2328,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2380,13 +2360,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b09161b..e52119e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -185,7 +179,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -217,12 +209,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -241,7 +231,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/75b27ef59cd0eb95b50d0cde14b05e0079b3ebe9.patch b/patches/75b27ef59cd0eb95b50d0cde14b05e0079b3ebe9.patch new file mode 100644 index 0000000..132c31e --- /dev/null +++ b/patches/75b27ef59cd0eb95b50d0cde14b05e0079b3ebe9.patch @@ -0,0 +1,1830 @@ +diff --git a/buffered.rs b/buffered.rs +index 3ba80e7..de9bc11 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -216,7 +209,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -236,7 +228,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -274,7 +265,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -294,7 +284,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -307,7 +296,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -418,7 +406,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -453,7 +440,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -468,7 +454,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -486,7 +471,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -533,7 +517,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -553,7 +536,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -571,7 +553,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -595,7 +576,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -604,7 +584,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -640,7 +619,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -653,7 +631,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -663,7 +640,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -702,7 +678,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -737,27 +712,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -828,7 +793,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -849,7 +813,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -870,7 +833,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -891,7 +853,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -916,7 +877,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -944,7 +904,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -952,7 +911,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1058,7 +1016,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index 9787cbb..1cf83d3 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -268,7 +259,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -279,15 +270,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -320,6 +320,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -348,6 +349,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -360,7 +362,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -378,7 +379,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -394,7 +395,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -410,8 +411,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index efe839d..d9fdaad 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -432,12 +396,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -466,8 +429,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -493,10 +455,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -509,8 +470,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -518,13 +477,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -532,33 +489,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index b7f82e6..c857f83 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -25,11 +29,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -40,7 +46,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -67,14 +72,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -97,7 +101,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -114,11 +118,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -129,7 +135,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -156,14 +162,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -207,7 +213,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -265,6 +270,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -274,7 +280,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -292,7 +298,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -333,7 +338,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 95c8934..b29907e 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,53 +257,43 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -330,6 +320,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -357,10 +348,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -496,7 +489,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -564,7 +556,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -575,7 +566,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -602,7 +592,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -655,7 +644,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -698,7 +687,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -761,7 +750,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -815,7 +803,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -857,7 +844,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -895,7 +881,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -934,7 +919,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -943,16 +927,59 @@ pub trait Read { + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -965,10 +992,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1003,7 +1029,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1027,7 +1052,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1037,7 +1061,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1050,11 +1073,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1067,10 +1088,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1104,7 +1124,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1128,7 +1147,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1139,13 +1157,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1159,21 +1175,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1227,7 +1240,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1276,7 +1288,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1287,7 +1298,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1315,7 +1325,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1348,7 +1357,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1401,7 +1409,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1457,7 +1464,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1492,7 +1498,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1508,7 +1513,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1546,7 +1550,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1585,7 +1588,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1597,29 +1599,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1698,7 +1697,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1739,7 +1738,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1761,7 +1759,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1817,7 +1814,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1876,7 +1872,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1917,7 +1912,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -1959,7 +1953,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -1974,7 +1967,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2000,7 +1992,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2023,7 +2014,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2050,20 +2040,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2091,7 +2078,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2116,7 +2103,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2151,7 +2137,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2179,7 +2164,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2204,7 +2188,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2229,7 +2212,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2258,13 +2240,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2282,6 +2262,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2290,7 +2271,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2317,13 +2298,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2347,14 +2326,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2379,13 +2358,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b09161b..e52119e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -185,7 +179,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -217,12 +209,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -241,7 +231,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/77f333b304424ae63dc70e10c6676dd645230f94.patch b/patches/77f333b304424ae63dc70e10c6676dd645230f94.patch new file mode 100644 index 0000000..6a4a6fc --- /dev/null +++ b/patches/77f333b304424ae63dc70e10c6676dd645230f94.patch @@ -0,0 +1,1964 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 16c18d6..f392e3c 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,6 +1,7 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DEFAULT_BUF_SIZE}; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -42,7 +43,6 @@ use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DE + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -66,7 +66,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -87,7 +86,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -117,7 +115,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -140,7 +137,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -168,7 +164,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -191,7 +186,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -215,7 +209,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -233,7 +226,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -253,7 +245,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -295,7 +286,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -315,7 +305,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -328,7 +317,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index 067ed6b..47869a7 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,7 +1,8 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -63,7 +64,6 @@ use crate::io::{ + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -85,7 +85,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -103,7 +102,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -198,7 +196,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -218,7 +215,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -236,7 +232,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -256,7 +251,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -280,7 +274,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -289,7 +282,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -353,7 +345,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -366,7 +357,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -377,7 +367,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index a80d08d..20bd401 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index f9caeaf..c21de5c 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,28 +119,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/cursor.rs b/cursor.rs +index bbee2cc..dc75216 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,8 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,8 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn get_ref(&self) -> &T { + &self.inner + } +@@ -152,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -176,8 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn position(&self) -> u64 { + self.pos + } +@@ -199,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -245,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -274,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -285,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -326,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -354,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -366,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -389,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -410,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -431,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 6642610..efbe402 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -230,7 +236,6 @@ impl Write for dyn ::realstd::io::LocalOutput { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -293,6 +298,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -302,7 +308,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -320,7 +326,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -366,7 +371,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index e6efe6e..e647c6b 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -247,57 +247,46 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print, LocalOutput}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-pub(crate) use self::stdio::clone_io; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + +-mod buffered; ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -324,6 +313,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -351,10 +341,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -488,7 +480,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -559,7 +550,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -571,7 +561,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -584,7 +573,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -608,7 +596,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -660,7 +647,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -703,7 +690,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -767,7 +754,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -821,7 +807,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -858,7 +843,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -896,7 +880,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -935,7 +918,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -944,22 +926,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -972,10 +996,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1010,7 +1033,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1034,7 +1056,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1044,7 +1065,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1057,18 +1077,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1081,10 +1097,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1118,7 +1133,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1142,7 +1156,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1153,13 +1166,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1173,21 +1184,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1241,7 +1249,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1288,7 +1295,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1301,7 +1307,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1316,7 +1321,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1344,7 +1348,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1378,7 +1381,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1440,7 +1442,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1493,7 +1494,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1549,7 +1549,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1584,7 +1583,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1598,7 +1596,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1635,7 +1632,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1673,7 +1669,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1683,29 +1678,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1781,7 +1773,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1822,7 +1814,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1844,7 +1835,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1901,7 +1891,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1964,7 +1953,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2003,7 +1991,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2040,7 +2027,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2055,7 +2041,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2081,7 +2066,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2104,7 +2088,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2131,20 +2114,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2172,7 +2152,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2197,7 +2177,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2230,7 +2209,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2258,7 +2236,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2283,7 +2260,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2308,7 +2284,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2337,13 +2312,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2361,6 +2334,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2369,7 +2343,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2396,13 +2370,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2426,14 +2398,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2458,13 +2430,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index 2b1f371..09f1aac 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,9 +3,10 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -45,7 +46,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -81,7 +81,6 @@ where + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -101,13 +100,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -119,7 +115,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -129,7 +126,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -140,7 +136,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -159,13 +154,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -195,7 +187,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -206,7 +197,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -227,13 +217,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -257,7 +244,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -281,7 +267,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/78e094632ec6160c3d2cfaad777c16a27ce08609.patch b/patches/78e094632ec6160c3d2cfaad777c16a27ce08609.patch new file mode 100644 index 0000000..9f404a6 --- /dev/null +++ b/patches/78e094632ec6160c3d2cfaad777c16a27ce08609.patch @@ -0,0 +1,1891 @@ +diff --git a/buffered.rs b/buffered.rs +index f3aadf2..3826382 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -49,7 +49,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -73,7 +72,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -94,7 +92,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -124,7 +121,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -147,7 +143,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -222,7 +215,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -240,7 +232,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -260,7 +251,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -302,7 +292,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -322,7 +311,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -335,7 +323,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -444,7 +431,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: Write::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: Write::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -479,7 +465,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -494,7 +479,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -512,7 +496,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -559,7 +542,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -579,7 +561,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -597,7 +578,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -617,7 +597,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -641,7 +620,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -650,7 +628,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -690,7 +667,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -703,7 +679,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -713,7 +688,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -753,7 +727,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -788,28 +761,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -878,7 +840,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -899,7 +860,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -920,7 +880,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -941,7 +900,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -966,7 +924,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -994,7 +951,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -1002,7 +958,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1103,7 +1058,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index 58343f6..6750136 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -67,7 +67,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -90,7 +89,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -108,7 +106,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -126,7 +123,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -147,7 +143,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -171,7 +166,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -193,13 +187,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -239,13 +231,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -268,7 +259,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -279,15 +270,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -320,6 +320,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -348,6 +349,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -360,7 +362,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -383,7 +384,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -404,7 +405,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -425,8 +426,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index e6eda2c..be46887 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -51,12 +56,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -66,13 +69,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -84,48 +90,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -137,10 +130,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -151,12 +142,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -164,7 +153,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -173,7 +161,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -204,7 +191,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -244,36 +230,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -299,7 +266,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -333,7 +299,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -369,12 +334,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -440,12 +404,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -476,8 +439,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -503,10 +465,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -519,8 +480,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -528,13 +487,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -542,34 +499,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 01dff0b..eb78a0f 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -30,11 +34,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -45,7 +51,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -77,14 +82,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -107,7 +111,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -129,11 +133,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -144,7 +150,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -176,14 +182,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -227,7 +233,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -290,6 +295,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -299,7 +305,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -317,7 +323,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -363,7 +368,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 3245629..7be5680 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -247,53 +247,43 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -320,6 +310,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -347,10 +338,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -484,7 +477,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -555,7 +547,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -567,7 +558,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -580,7 +570,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -604,7 +593,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -656,7 +644,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -699,7 +687,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -763,7 +751,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -817,7 +804,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -854,7 +840,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -892,7 +877,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -931,7 +915,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -940,22 +923,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -968,10 +993,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1006,7 +1030,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1030,7 +1053,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1040,7 +1062,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1053,18 +1074,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1077,10 +1094,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1114,7 +1130,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1138,7 +1153,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1149,13 +1163,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1169,21 +1181,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1237,7 +1246,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1284,7 +1292,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1297,7 +1304,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1312,7 +1318,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1340,7 +1345,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1374,7 +1378,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1436,7 +1439,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1489,7 +1491,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1545,7 +1546,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1580,7 +1580,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1594,7 +1593,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1631,7 +1629,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1669,7 +1666,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1679,29 +1675,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1777,7 +1770,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1818,7 +1811,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1840,7 +1832,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1897,7 +1888,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1960,7 +1950,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1999,7 +1988,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2036,7 +2024,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2051,7 +2038,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2077,7 +2063,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2100,7 +2085,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2127,20 +2111,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2168,7 +2149,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2193,7 +2174,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2226,7 +2206,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2254,7 +2233,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2279,7 +2257,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2304,7 +2281,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2333,13 +2309,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2357,6 +2331,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2365,7 +2340,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2392,13 +2367,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2422,14 +2395,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2454,13 +2427,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index a093b74..1e468ae 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -42,7 +43,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -75,7 +75,6 @@ where + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -95,12 +94,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -112,7 +109,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -122,7 +120,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -133,7 +130,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -152,12 +148,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -187,7 +181,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -219,12 +211,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -248,7 +238,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/7a5d3abfb1aa3a38e0b3b3508c760fc8e712226c.patch b/patches/7a5d3abfb1aa3a38e0b3b3508c760fc8e712226c.patch new file mode 100644 index 0000000..cfc1572 --- /dev/null +++ b/patches/7a5d3abfb1aa3a38e0b3b3508c760fc8e712226c.patch @@ -0,0 +1,1891 @@ +diff --git a/buffered.rs b/buffered.rs +index b4c91cc..3c3cad2 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -197,7 +191,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -221,7 +214,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -239,7 +231,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -259,7 +250,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -301,7 +291,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -321,7 +310,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -334,7 +322,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -445,7 +432,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -480,7 +466,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -495,7 +480,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -513,7 +497,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -560,7 +543,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -580,7 +562,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -598,7 +579,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -618,7 +598,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -642,7 +621,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -651,7 +629,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -691,7 +668,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -704,7 +680,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -714,7 +689,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -753,7 +727,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -788,28 +761,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -880,7 +842,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -901,7 +862,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -922,7 +882,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -943,7 +902,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -968,7 +926,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -996,7 +953,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -1004,7 +960,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1105,7 +1060,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index f4db5f8..4f20b8a 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -272,7 +263,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -283,15 +274,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -324,6 +324,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -352,6 +353,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -364,7 +366,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -387,7 +388,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -408,7 +409,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -429,8 +430,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index f7248e7..f7311ad 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,12 +143,10 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -165,7 +154,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -174,7 +162,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -205,7 +192,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -248,36 +234,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -303,7 +270,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -334,7 +300,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -368,12 +333,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -437,12 +401,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -471,8 +434,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -498,10 +460,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -514,8 +475,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -523,13 +482,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -537,34 +494,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 01dff0b..eb78a0f 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -30,11 +34,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -45,7 +51,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -77,14 +82,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -107,7 +111,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -129,11 +133,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -144,7 +150,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -176,14 +182,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -227,7 +233,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -290,6 +295,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -299,7 +305,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -317,7 +323,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -363,7 +368,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 9eb54c2..15e51d3 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -247,53 +247,43 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -320,6 +310,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -347,10 +338,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -484,7 +477,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -555,7 +547,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -567,7 +558,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -580,7 +570,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -604,7 +593,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -656,7 +644,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -699,7 +687,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -763,7 +751,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -817,7 +804,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -855,7 +841,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -893,7 +878,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -932,7 +916,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -941,22 +924,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -969,10 +994,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1007,7 +1031,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1031,7 +1054,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1041,7 +1063,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1054,18 +1075,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1078,10 +1095,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1115,7 +1131,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1139,7 +1154,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1150,13 +1164,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1170,21 +1182,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1238,7 +1247,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Self::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1283,7 +1291,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1294,7 +1301,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1307,7 +1313,6 @@ pub trait Write { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1335,7 +1340,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1369,7 +1373,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1432,7 +1435,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1485,7 +1487,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1541,7 +1542,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1576,7 +1576,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1592,7 +1591,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1630,7 +1628,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1669,7 +1666,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1681,29 +1677,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1782,7 +1775,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1823,7 +1816,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1845,7 +1837,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: Self::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1905,7 +1896,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1968,7 +1958,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2009,7 +1998,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2048,7 +2036,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2063,7 +2050,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2089,7 +2075,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2112,7 +2097,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2139,20 +2123,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2180,7 +2161,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2205,7 +2186,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2238,7 +2218,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2266,7 +2245,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2291,7 +2269,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2316,7 +2293,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2345,13 +2321,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2369,6 +2343,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2377,7 +2352,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2404,13 +2379,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2434,14 +2407,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2466,13 +2439,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b9d5dc2..07d090e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -190,7 +184,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -203,7 +196,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -222,12 +214,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -251,7 +241,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/7c84ba112429eb9bc0b99a6fe32a453c920a764c.patch b/patches/7c84ba112429eb9bc0b99a6fe32a453c920a764c.patch new file mode 100644 index 0000000..43e54de --- /dev/null +++ b/patches/7c84ba112429eb9bc0b99a6fe32a453c920a764c.patch @@ -0,0 +1,1848 @@ +diff --git a/buffered.rs b/buffered.rs +index 8862226..7898006 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -222,7 +215,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -240,7 +232,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -260,7 +251,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -298,7 +288,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -318,7 +307,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -331,7 +319,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -442,7 +429,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -477,7 +463,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -492,7 +477,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -510,7 +494,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -557,7 +540,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -577,7 +559,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -595,7 +576,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -616,7 +596,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -640,7 +619,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -649,7 +627,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -685,7 +662,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -698,7 +674,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -708,7 +683,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -747,7 +721,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -782,28 +755,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -874,7 +836,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -895,7 +856,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -916,7 +876,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -937,7 +896,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -962,7 +920,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -990,7 +947,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -998,7 +954,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1104,7 +1059,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index 9787cbb..1cf83d3 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -268,7 +259,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -279,15 +270,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -320,6 +320,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -348,6 +349,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -360,7 +362,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -378,7 +379,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -394,7 +395,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -410,8 +411,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index 3b55d9b..c754d1f 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -432,12 +396,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -466,8 +429,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -493,10 +455,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -509,8 +470,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -518,13 +477,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -532,34 +489,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index b7f82e6..c857f83 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -25,11 +29,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -40,7 +46,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -67,14 +72,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -97,7 +101,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -114,11 +118,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -129,7 +135,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -156,14 +162,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -207,7 +213,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -265,6 +270,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -274,7 +280,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -292,7 +298,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -333,7 +338,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index a50dd95..d76672a 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,53 +257,43 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -330,6 +320,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -357,10 +348,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -496,7 +489,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -564,7 +556,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -575,7 +566,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -602,7 +592,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -655,7 +644,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -698,7 +687,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -761,7 +750,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -815,7 +803,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -857,7 +844,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -895,7 +881,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -934,7 +919,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -943,16 +927,59 @@ pub trait Read { + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -965,10 +992,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1003,7 +1029,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1027,7 +1052,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1037,7 +1061,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1050,11 +1073,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1067,10 +1088,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1104,7 +1124,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1128,7 +1147,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1139,13 +1157,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1159,21 +1175,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1227,7 +1240,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1276,7 +1288,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1287,7 +1298,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1315,7 +1325,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1350,7 +1359,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1403,7 +1411,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1459,7 +1466,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1494,7 +1500,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1510,7 +1515,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1548,7 +1552,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1587,7 +1590,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1599,29 +1601,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1700,7 +1699,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1741,7 +1740,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1763,7 +1761,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1819,7 +1816,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1878,7 +1874,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1919,7 +1914,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -1961,7 +1955,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -1976,7 +1969,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2002,7 +1994,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2025,7 +2016,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2052,20 +2042,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2093,7 +2080,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2118,7 +2105,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2153,7 +2139,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2181,7 +2166,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2206,7 +2190,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2231,7 +2214,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2260,13 +2242,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2284,6 +2264,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2292,7 +2273,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2319,13 +2300,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2349,14 +2328,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2381,13 +2360,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b09161b..e52119e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -185,7 +179,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -217,12 +209,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -241,7 +231,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/7d6af6751c5726d884440d4e8d462a9ee6c5efc1.patch b/patches/7d6af6751c5726d884440d4e8d462a9ee6c5efc1.patch new file mode 100644 index 0000000..9661daa --- /dev/null +++ b/patches/7d6af6751c5726d884440d4e8d462a9ee6c5efc1.patch @@ -0,0 +1,2091 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 02b0fc0..fe6e4af 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,8 +1,9 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, SizeHint, DEFAULT_BUF_SIZE, + }; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -44,7 +45,6 @@ use crate::io::{ + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -68,7 +68,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -89,7 +88,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buf = Box::new_uninit_slice(capacity).assume_init(); +@@ -118,7 +116,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -141,7 +138,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -169,7 +165,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -192,7 +187,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -216,7 +210,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -234,7 +227,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -254,7 +246,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -310,7 +301,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -330,7 +320,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -343,7 +332,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index 80f98bb..d11d026 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,9 +1,9 @@ +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; +-use crate::mem; ++use core::mem; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -65,7 +65,6 @@ use crate::mem; + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -87,7 +86,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -105,7 +103,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -200,7 +197,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -220,7 +216,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -238,7 +233,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -270,7 +264,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -294,7 +287,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -325,7 +317,6 @@ impl BufWriter { + /// assert_eq!(recovered_writer.len(), 0); + /// assert_eq!(&buffered_data.unwrap(), b"ata"); + /// ``` +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_raw_parts(mut self) -> (W, Result, WriterPanicked>) { + let buf = mem::take(&mut self.buf); + let buf = if !self.panicked { Ok(buf) } else { Err(WriterPanicked { buf }) }; +@@ -333,7 +324,6 @@ impl BufWriter { + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + /// Error returned for the buffered data from `BufWriter::into_raw_parts`, when the underlying + /// writer has previously panicked. Contains the (possibly partly written) buffered data. + /// +@@ -367,7 +357,6 @@ pub struct WriterPanicked { + impl WriterPanicked { + /// Returns the perhaps-unwritten data. Some of this data may have been written by the + /// panicking call(s) to the underlying writer, so simply writing it again is not a good idea. +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_inner(self) -> Vec { + self.buf + } +@@ -376,22 +365,12 @@ impl WriterPanicked { + "BufWriter inner writer panicked, what data remains unwritten is not known"; + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] +-impl error::Error for WriterPanicked { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- Self::DESCRIPTION +- } +-} +- +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Display for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + write!(f, "{}", Self::DESCRIPTION) + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Debug for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("WriterPanicked") +@@ -400,7 +379,6 @@ impl fmt::Debug for WriterPanicked { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -497,7 +475,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -510,7 +487,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -521,7 +497,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index d7b620d..1804305 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index d0c859d..a052adf 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index 6549781..0dc7440 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,7 +119,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } +@@ -143,7 +139,6 @@ impl IntoInnerError { + /// let err = into_inner_err.into_error(); + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_error(self) -> Error { + self.1 + } +@@ -167,28 +162,17 @@ impl IntoInnerError { + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// assert_eq!(recovered_writer.buffer(), b"t be actually written"); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_parts(self) -> (Error, W) { + (self.1, self.0) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/copy.rs b/copy.rs +index eb60df2..df99a47 100644 +--- a/copy.rs ++++ b/copy.rs +@@ -1,5 +1,6 @@ +-use super::{BufWriter, ErrorKind, Read, Result, Write, DEFAULT_BUF_SIZE}; +-use crate::mem::MaybeUninit; ++use super::{ErrorKind, Read, Result, Write, DEFAULT_BUF_SIZE}; ++#[cfg(feature = "collections")] use super::BufWriter; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,19 +40,12 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> Result + where + R: Read, + W: Write, + { +- cfg_if::cfg_if! { +- if #[cfg(any(target_os = "linux", target_os = "android"))] { +- crate::sys::kernel_copy::copy_spec(reader, writer) +- } else { +- generic_copy(reader, writer) +- } +- } ++ generic_copy(reader, writer) + } + + /// The userspace read-write-loop implementation of `io::copy` that is used when +@@ -76,6 +70,7 @@ impl BufferedCopySpec for W { + } + } + ++#[cfg(feature = "collections")] + impl BufferedCopySpec for BufWriter { + fn copy_to(reader: &mut R, writer: &mut Self) -> Result { + if writer.capacity() < DEFAULT_BUF_SIZE { +diff --git a/cursor.rs b/cursor.rs +index 9021b47..49ebb05 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,8 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,8 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn get_ref(&self) -> &T { + &self.inner + } +@@ -152,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -176,8 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn position(&self) -> u64 { + self.pos + } +@@ -199,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -245,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -274,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -285,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -326,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new_const( +@@ -354,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -366,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -389,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -410,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -431,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index 97c92aa..2dd6c9b 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -71,13 +74,16 @@ enum Repr { + Simple(ErrorKind), + // &str is a fat pointer, but &&str is a thin pointer. + SimpleMessage(ErrorKind, &'static &'static str), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -89,48 +95,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -142,10 +135,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -156,12 +147,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -169,7 +158,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -178,7 +166,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -209,7 +196,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -249,15 +235,14 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +@@ -274,25 +259,6 @@ impl Error { + Self { repr: Repr::SimpleMessage(kind, message) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[inline] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -318,7 +284,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + #[inline] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } +@@ -353,7 +318,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + #[inline] + pub fn raw_os_error(&self) -> Option { + match self.repr { +@@ -391,14 +355,13 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] + #[inline] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, + Repr::SimpleMessage(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -464,14 +427,13 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] + #[inline] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, + Repr::SimpleMessage(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -502,9 +464,8 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] + #[inline] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -531,11 +492,10 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + #[inline] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + Repr::SimpleMessage(kind, _) => kind, +@@ -549,8 +509,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -561,13 +519,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -576,37 +532,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::SimpleMessage(_, &msg) => msg, +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::SimpleMessage(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::SimpleMessage(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 6891bd8..22b2b02 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,18 +1,22 @@ + #[cfg(test)] + mod tests; + +-use crate::alloc::Allocator; +-use crate::cmp; +-use crate::fmt; ++#[cfg(feature="collections")] use core::alloc::Allocator; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -34,11 +38,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -49,7 +55,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -81,14 +86,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -111,7 +115,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -133,11 +137,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -148,7 +154,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -180,14 +186,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -217,7 +223,6 @@ impl BufRead for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -280,6 +285,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -289,7 +295,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -311,7 +317,6 @@ impl BufRead for &[u8] { + /// If the number of bytes to be written exceeds the size of the slice, write operations will + /// return short writes: ultimately, `Ok(0)`; in this situation, `write_all` returns an error of + /// kind `ErrorKind::WriteZero`. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -357,7 +362,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 9953bcd..700f624 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -246,58 +246,48 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::copy::copy; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[unstable(feature = "internal_output_capture", issue = "none")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::set_output_capture; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + pub(crate) mod copy; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -324,6 +314,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -351,10 +342,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -504,7 +497,6 @@ pub(crate) fn default_read_exact(this: &mut R, mut buf: &mut [ + /// [`&str`]: prim@str + /// [`std::io`]: self + /// [`File`]: crate::fs::File +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -580,7 +572,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -592,7 +583,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -605,7 +595,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -629,7 +618,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -681,7 +669,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -724,7 +712,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -788,7 +776,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, buf: &mut [u8]) -> Result<()> { + default_read_exact(self, buf) + } +@@ -827,7 +814,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -864,7 +850,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -902,7 +887,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -941,7 +925,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -991,29 +974,71 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +-#[unstable(feature = "io_read_to_string", issue = "80218")] ++#[cfg(feature="collections")] + pub fn read_to_string(reader: &mut R) -> Result { + let mut buf = String::new(); + reader.read_to_string(&mut buf)?; + Ok(buf) + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1026,10 +1051,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1064,7 +1088,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1088,7 +1111,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1098,7 +1120,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1111,18 +1132,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1135,10 +1152,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1172,7 +1188,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1196,7 +1211,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1207,13 +1221,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1227,21 +1239,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1295,7 +1304,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1342,7 +1350,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1355,7 +1362,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1370,7 +1376,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1398,7 +1403,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1432,7 +1436,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1497,7 +1500,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1553,7 +1555,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1609,7 +1610,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1644,7 +1644,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1658,7 +1657,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1695,7 +1693,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_stream_len", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1732,7 +1729,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "seek_convenience", since = "1.51.0")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1742,29 +1738,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1840,7 +1833,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1881,7 +1874,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1903,7 +1895,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1960,7 +1951,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -2023,7 +2013,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2061,7 +2050,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2098,7 +2086,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2113,7 +2100,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Chain { + first: T, +@@ -2140,7 +2126,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2163,7 +2148,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2190,13 +2174,11 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2224,7 +2206,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2262,7 +2244,6 @@ impl SizeHint for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2295,7 +2276,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2323,7 +2303,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2348,7 +2327,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2373,7 +2351,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2402,13 +2379,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2426,6 +2401,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2434,7 +2410,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2461,13 +2437,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2515,14 +2489,14 @@ impl SizeHint for T { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2547,13 +2521,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index d806431..6b9791a 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index f472361..0a1899d 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,16 +3,16 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; ++use core::fmt; + use crate::io::{ +- self, BufRead, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, SizeHint, Write, ++ self, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, SizeHint, Write, + }; ++#[cfg(feature="collections")] use crate::io::BufRead; + + /// A reader which is always at EOF. + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -32,13 +32,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -50,7 +47,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -60,7 +58,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "empty_seek", since = "1.51.0")] + impl Seek for Empty { + fn seek(&mut self, _pos: SeekFrom) -> io::Result { + Ok(0) +@@ -75,7 +72,6 @@ impl Seek for Empty { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -92,7 +88,6 @@ impl SizeHint for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -111,13 +106,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -147,7 +139,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -158,7 +149,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -179,13 +169,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -209,7 +196,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -233,7 +219,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/83980aca2086e5c4dca5aae9a92a065a9ff4ac56.patch b/patches/83980aca2086e5c4dca5aae9a92a065a9ff4ac56.patch new file mode 100644 index 0000000..9f39ae0 --- /dev/null +++ b/patches/83980aca2086e5c4dca5aae9a92a065a9ff4ac56.patch @@ -0,0 +1,1848 @@ +diff --git a/buffered.rs b/buffered.rs +index 8862226..7898006 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -222,7 +215,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -240,7 +232,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -260,7 +251,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -298,7 +288,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -318,7 +307,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -331,7 +319,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -442,7 +429,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -477,7 +463,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -492,7 +477,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -510,7 +494,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -557,7 +540,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -577,7 +559,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -595,7 +576,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -616,7 +596,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -640,7 +619,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -649,7 +627,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -685,7 +662,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -698,7 +674,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -708,7 +683,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -747,7 +721,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -782,28 +755,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -874,7 +836,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -895,7 +856,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -916,7 +876,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -937,7 +896,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -962,7 +920,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -990,7 +947,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -998,7 +954,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1104,7 +1059,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index f36aa18..89d0701 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -268,7 +259,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -279,15 +270,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -320,6 +320,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -348,6 +349,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -360,7 +362,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -378,7 +379,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -394,7 +395,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -410,8 +411,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index 3b55d9b..c754d1f 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -432,12 +396,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -466,8 +429,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -493,10 +455,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -509,8 +470,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -518,13 +477,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -532,34 +489,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index b7f82e6..c857f83 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -25,11 +29,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -40,7 +46,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -67,14 +72,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -97,7 +101,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -114,11 +118,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -129,7 +135,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -156,14 +162,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -207,7 +213,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -265,6 +270,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -274,7 +280,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -292,7 +298,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -333,7 +338,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 0103e4b..712cb5c 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,53 +257,43 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -330,6 +320,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -357,10 +348,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -496,7 +489,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -564,7 +556,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -575,7 +566,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -602,7 +592,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -655,7 +644,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -698,7 +687,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -761,7 +750,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -815,7 +803,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -857,7 +844,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -895,7 +881,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -934,7 +919,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -943,16 +927,59 @@ pub trait Read { + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -965,10 +992,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1003,7 +1029,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1027,7 +1052,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1037,7 +1061,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1050,11 +1073,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1067,10 +1088,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1104,7 +1124,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1128,7 +1147,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1139,13 +1157,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1159,21 +1175,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1227,7 +1240,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1276,7 +1288,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1287,7 +1298,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1315,7 +1325,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1350,7 +1359,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1403,7 +1411,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1459,7 +1466,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1494,7 +1500,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1510,7 +1515,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1548,7 +1552,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1587,7 +1590,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1599,29 +1601,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1700,7 +1699,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1741,7 +1740,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1763,7 +1761,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1819,7 +1816,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1878,7 +1874,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1919,7 +1914,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -1961,7 +1955,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -1976,7 +1969,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2002,7 +1994,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2025,7 +2016,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2052,20 +2042,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2093,7 +2080,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2118,7 +2105,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2153,7 +2139,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2181,7 +2166,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2206,7 +2190,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2231,7 +2214,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2260,13 +2242,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2284,6 +2264,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2292,7 +2273,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2319,13 +2300,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2349,14 +2328,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2381,13 +2360,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b09161b..e52119e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -185,7 +179,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -217,12 +209,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -241,7 +231,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/8a18fb0f7396ceb1ca18cd82ca3deb795f5e60b2.patch b/patches/8a18fb0f7396ceb1ca18cd82ca3deb795f5e60b2.patch new file mode 100644 index 0000000..875fbdb --- /dev/null +++ b/patches/8a18fb0f7396ceb1ca18cd82ca3deb795f5e60b2.patch @@ -0,0 +1,2060 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 987371f..d2af8b8 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,6 +1,7 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DEFAULT_BUF_SIZE}; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -42,7 +43,6 @@ use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DE + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -66,7 +66,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -87,7 +86,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -117,7 +115,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -140,7 +137,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -168,7 +164,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -191,7 +186,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -215,7 +209,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -233,7 +226,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -253,7 +245,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -309,7 +300,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -329,7 +319,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -342,7 +331,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index fa7bd0d..061c4c9 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,9 +1,9 @@ +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; +-use crate::mem; ++use core::mem; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -65,7 +65,6 @@ use crate::mem; + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -87,7 +86,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -105,7 +103,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -200,7 +197,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -220,7 +216,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -238,7 +233,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -258,7 +252,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -282,7 +275,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -313,7 +305,6 @@ impl BufWriter { + /// assert_eq!(recovered_writer.len(), 0); + /// assert_eq!(&buffered_data.unwrap(), b"ata"); + /// ``` +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_raw_parts(mut self) -> (W, Result, WriterPanicked>) { + let buf = mem::take(&mut self.buf); + let buf = if !self.panicked { Ok(buf) } else { Err(WriterPanicked { buf }) }; +@@ -321,7 +312,6 @@ impl BufWriter { + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + /// Error returned for the buffered data from `BufWriter::into_raw_parts`, when the underlying + /// writer has previously panicked. Contains the (possibly partly written) buffered data. + /// +@@ -355,7 +345,6 @@ pub struct WriterPanicked { + impl WriterPanicked { + /// Returns the perhaps-unwritten data. Some of this data may have been written by the + /// panicking call(s) to the underlying writer, so simply writing it again is not a good idea. +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_inner(self) -> Vec { + self.buf + } +@@ -364,22 +353,12 @@ impl WriterPanicked { + "BufWriter inner writer panicked, what data remains unwritten is not known"; + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] +-impl error::Error for WriterPanicked { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- Self::DESCRIPTION +- } +-} +- +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Display for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + write!(f, "{}", Self::DESCRIPTION) + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Debug for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("WriterPanicked") +@@ -388,7 +367,6 @@ impl fmt::Debug for WriterPanicked { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -485,7 +463,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -498,7 +475,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -509,7 +485,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index d0c859d..a052adf 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index 6549781..0dc7440 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,7 +119,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } +@@ -143,7 +139,6 @@ impl IntoInnerError { + /// let err = into_inner_err.into_error(); + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_error(self) -> Error { + self.1 + } +@@ -167,28 +162,17 @@ impl IntoInnerError { + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// assert_eq!(recovered_writer.buffer(), b"t be actually written"); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_parts(self) -> (Error, W) { + (self.1, self.0) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/copy.rs b/copy.rs +index b88bca2..7593702 100644 +--- a/copy.rs ++++ b/copy.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, ErrorKind, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,19 +39,12 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, + W: Write, + { +- cfg_if::cfg_if! { +- if #[cfg(any(target_os = "linux", target_os = "android"))] { +- crate::sys::kernel_copy::copy_spec(reader, writer) +- } else { +- generic_copy(reader, writer) +- } +- } ++ generic_copy(reader, writer) + } + + /// The general read-write-loop implementation of +diff --git a/cursor.rs b/cursor.rs +index bbee2cc..dc75216 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,8 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,8 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn get_ref(&self) -> &T { + &self.inner + } +@@ -152,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -176,8 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn position(&self) -> u64 { + self.pos + } +@@ -199,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -245,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -274,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -285,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -326,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -354,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -366,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -389,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -410,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -431,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 00bf8b9..5c0e7cd 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -216,7 +222,6 @@ impl BufRead for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -279,6 +284,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -288,7 +294,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -310,7 +316,6 @@ impl BufRead for &[u8] { + /// If the number of bytes to be written exceeds the size of the slice, write operations will + /// return short writes: ultimately, `Ok(0)`; in this situation, `write_all` returns an error of + /// kind `ErrorKind::WriteZero`. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -356,7 +361,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index db3b0e2..6e3a4c5 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -246,58 +246,48 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::copy::copy; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[unstable(feature = "internal_output_capture", issue = "none")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::set_output_capture; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + pub(crate) mod copy; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -324,6 +314,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -351,10 +342,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -505,7 +498,6 @@ pub(crate) fn default_read_exact(this: &mut R, mut buf: &mut [ + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -576,7 +568,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -588,7 +579,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -601,7 +591,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -625,7 +614,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -677,7 +665,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -720,7 +708,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -784,7 +772,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, buf: &mut [u8]) -> Result<()> { + default_read_exact(self, buf) + } +@@ -823,7 +810,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -860,7 +846,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -898,7 +883,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -937,7 +921,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -987,29 +970,71 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +-#[unstable(feature = "io_read_to_string", issue = "80218")] ++#[cfg(feature="collections")] + pub fn read_to_string(reader: &mut R) -> Result { + let mut buf = String::new(); + reader.read_to_string(&mut buf)?; + Ok(buf) + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1022,10 +1047,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1060,7 +1084,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1084,7 +1107,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1094,7 +1116,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1107,18 +1128,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1131,10 +1148,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1168,7 +1184,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1192,7 +1207,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1203,13 +1217,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1223,21 +1235,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1291,7 +1300,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1338,7 +1346,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1351,7 +1358,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1366,7 +1372,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1394,7 +1399,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1428,7 +1432,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1490,7 +1493,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1543,7 +1545,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1599,7 +1600,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1634,7 +1634,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1648,7 +1647,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1685,7 +1683,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_stream_len", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1722,7 +1719,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "seek_convenience", since = "1.51.0")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1732,29 +1728,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1830,7 +1823,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1871,7 +1864,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1893,7 +1885,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1950,7 +1941,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -2013,7 +2003,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2051,7 +2040,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2088,7 +2076,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2103,7 +2090,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2129,7 +2115,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2152,7 +2137,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2179,20 +2163,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2220,7 +2201,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2245,7 +2226,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2278,7 +2258,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2306,7 +2285,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2331,7 +2309,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2356,7 +2333,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2385,13 +2361,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2409,6 +2383,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2417,7 +2392,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2444,13 +2419,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2474,14 +2447,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2506,13 +2479,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index d806431..6b9791a 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index db84545..8e88c3d 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,14 +3,14 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, Initializer, IoSlice, IoSliceMut, Read, Write}; ++use core::fmt; ++use crate::io::{self, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; + + /// A reader which is always at EOF. + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -30,13 +30,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -48,7 +45,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -58,7 +56,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -69,7 +66,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -88,13 +84,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -124,7 +117,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -135,7 +127,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -156,13 +147,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -186,7 +174,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -210,7 +197,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/8cef65fde3f92a84218fc338de6ab967fafd1820.patch b/patches/8cef65fde3f92a84218fc338de6ab967fafd1820.patch new file mode 100644 index 0000000..972ad09 --- /dev/null +++ b/patches/8cef65fde3f92a84218fc338de6ab967fafd1820.patch @@ -0,0 +1,2002 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 16c18d6..f392e3c 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,6 +1,7 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DEFAULT_BUF_SIZE}; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -42,7 +43,6 @@ use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DE + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -66,7 +66,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -87,7 +86,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -117,7 +115,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -140,7 +137,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -168,7 +164,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -191,7 +186,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -215,7 +209,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -233,7 +226,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -253,7 +245,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -295,7 +286,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -315,7 +305,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -328,7 +317,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index 3b33998..d20db36 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,7 +1,8 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -63,7 +64,6 @@ use crate::io::{ + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -85,7 +85,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -103,7 +102,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -198,7 +196,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -218,7 +215,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -236,7 +232,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -256,7 +251,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -280,7 +274,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -289,7 +282,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -386,7 +378,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -399,7 +390,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -410,7 +400,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index d0c859d..a052adf 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index 6549781..0dc7440 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,7 +119,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } +@@ -143,7 +139,6 @@ impl IntoInnerError { + /// let err = into_inner_err.into_error(); + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_error(self) -> Error { + self.1 + } +@@ -167,28 +162,17 @@ impl IntoInnerError { + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// assert_eq!(recovered_writer.buffer(), b"t be actually written"); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_parts(self) -> (Error, W) { + (self.1, self.0) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/copy.rs b/copy.rs +index b88bca2..7593702 100644 +--- a/copy.rs ++++ b/copy.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, ErrorKind, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,19 +39,12 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, + W: Write, + { +- cfg_if::cfg_if! { +- if #[cfg(any(target_os = "linux", target_os = "android"))] { +- crate::sys::kernel_copy::copy_spec(reader, writer) +- } else { +- generic_copy(reader, writer) +- } +- } ++ generic_copy(reader, writer) + } + + /// The general read-write-loop implementation of +diff --git a/cursor.rs b/cursor.rs +index bbee2cc..dc75216 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,8 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,8 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn get_ref(&self) -> &T { + &self.inner + } +@@ -152,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -176,8 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn position(&self) -> u64 { + self.pos + } +@@ -199,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -245,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -274,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -285,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -326,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -354,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -366,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -389,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -410,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -431,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 00bf8b9..5c0e7cd 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -216,7 +222,6 @@ impl BufRead for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -279,6 +284,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -288,7 +294,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -310,7 +316,6 @@ impl BufRead for &[u8] { + /// If the number of bytes to be written exceeds the size of the slice, write operations will + /// return short writes: ultimately, `Ok(0)`; in this situation, `write_all` returns an error of + /// kind `ErrorKind::WriteZero`. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -356,7 +361,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index dfbf6c3..7437b18 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -247,58 +247,48 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::copy::copy; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[unstable(feature = "internal_output_capture", issue = "none")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::set_output_capture; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + pub(crate) mod copy; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -325,6 +315,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -352,10 +343,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -489,7 +482,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -560,7 +552,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -572,7 +563,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -585,7 +575,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -609,7 +598,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -661,7 +649,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -704,7 +692,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -768,7 +756,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -822,7 +809,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -859,7 +845,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -897,7 +882,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -936,7 +920,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -945,22 +928,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -973,10 +998,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1011,7 +1035,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1035,7 +1058,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1045,7 +1067,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1058,18 +1079,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1082,10 +1099,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1119,7 +1135,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1143,7 +1158,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1154,13 +1168,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1174,21 +1186,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1242,7 +1251,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1289,7 +1297,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1302,7 +1309,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1317,7 +1323,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1345,7 +1350,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1379,7 +1383,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1441,7 +1444,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1494,7 +1496,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1550,7 +1551,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1585,7 +1585,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1599,7 +1598,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1636,7 +1634,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1674,7 +1671,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1684,29 +1680,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1782,7 +1775,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1823,7 +1816,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1845,7 +1837,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1902,7 +1893,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1965,7 +1955,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2004,7 +1993,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2041,7 +2029,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2056,7 +2043,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2082,7 +2068,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2105,7 +2090,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2132,20 +2116,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2173,7 +2154,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2198,7 +2179,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2231,7 +2211,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2259,7 +2238,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2284,7 +2262,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2309,7 +2286,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2338,13 +2314,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2362,6 +2336,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2370,7 +2345,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2397,13 +2372,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2427,14 +2400,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2459,13 +2432,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index db84545..8e88c3d 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,14 +3,14 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, Initializer, IoSlice, IoSliceMut, Read, Write}; ++use core::fmt; ++use crate::io::{self, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; + + /// A reader which is always at EOF. + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -30,13 +30,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -48,7 +45,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -58,7 +56,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -69,7 +66,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -88,13 +84,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -124,7 +117,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -135,7 +127,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -156,13 +147,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -186,7 +174,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -210,7 +197,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/8d470b57968fd875c2d9ce50446868b906f54752.patch b/patches/8d470b57968fd875c2d9ce50446868b906f54752.patch new file mode 100644 index 0000000..4a71591 --- /dev/null +++ b/patches/8d470b57968fd875c2d9ce50446868b906f54752.patch @@ -0,0 +1,1893 @@ +diff --git a/buffered.rs b/buffered.rs +index b4c91cc..3c3cad2 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -197,7 +191,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -221,7 +214,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -239,7 +231,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -259,7 +250,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -301,7 +291,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -321,7 +310,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -334,7 +322,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -445,7 +432,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -480,7 +466,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -495,7 +480,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -513,7 +497,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -560,7 +543,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -580,7 +562,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -598,7 +579,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -618,7 +598,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -642,7 +621,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -651,7 +629,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -691,7 +668,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -704,7 +680,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -714,7 +689,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -753,7 +727,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -788,28 +761,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -880,7 +842,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -901,7 +862,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -922,7 +882,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -943,7 +902,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -968,7 +926,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -996,7 +953,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -1004,7 +960,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1105,7 +1060,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index f4db5f8..4f20b8a 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -272,7 +263,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -283,15 +274,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -324,6 +324,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -352,6 +353,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -364,7 +366,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -387,7 +388,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -408,7 +409,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -429,8 +430,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index f7248e7..f7311ad 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,12 +143,10 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -165,7 +154,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -174,7 +162,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -205,7 +192,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -248,36 +234,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -303,7 +270,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -334,7 +300,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -368,12 +333,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -437,12 +401,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -471,8 +434,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -498,10 +460,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -514,8 +475,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -523,13 +482,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -537,34 +494,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 01dff0b..eb78a0f 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -30,11 +34,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -45,7 +51,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -77,14 +82,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -107,7 +111,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -129,11 +133,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -144,7 +150,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -176,14 +182,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -227,7 +233,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -290,6 +295,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -299,7 +305,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -317,7 +323,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -363,7 +368,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 823ce30..f0f3edf 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -247,54 +247,44 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::mem; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++use core::mem; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -321,6 +311,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -348,10 +339,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -485,7 +478,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -556,7 +548,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -568,7 +559,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -581,7 +571,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -605,7 +594,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -657,7 +645,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -700,7 +688,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -761,7 +749,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -815,7 +802,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -853,7 +839,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -891,7 +876,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -930,7 +914,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -939,22 +922,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -967,10 +992,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1005,7 +1029,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1029,7 +1052,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1039,7 +1061,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1052,18 +1073,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1076,10 +1093,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1113,7 +1129,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1137,7 +1152,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1148,13 +1162,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1168,21 +1180,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1236,7 +1245,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Self::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1281,7 +1289,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1292,7 +1299,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1305,7 +1311,6 @@ pub trait Write { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1333,7 +1338,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1367,7 +1371,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1430,7 +1433,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + while !bufs.is_empty() { + match self.write_vectored(bufs) { +@@ -1480,7 +1482,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1536,7 +1537,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1571,7 +1571,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1587,7 +1586,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1625,7 +1623,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1664,7 +1661,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1676,29 +1672,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1777,7 +1770,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1818,7 +1811,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1840,7 +1832,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: Self::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1900,7 +1891,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1963,7 +1953,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2004,7 +1993,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2043,7 +2031,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2058,7 +2045,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2084,7 +2070,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2107,7 +2092,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2134,20 +2118,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2175,7 +2156,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2200,7 +2181,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2233,7 +2213,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2261,7 +2240,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2286,7 +2264,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2311,7 +2288,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2340,13 +2316,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2364,6 +2338,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2372,7 +2347,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2399,13 +2374,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2429,14 +2402,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2461,13 +2434,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b9d5dc2..07d090e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -190,7 +184,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -203,7 +196,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -222,12 +214,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -251,7 +241,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/8d48e3bbb2da2f5eb5f4a95efd6846e9ea93a160.patch b/patches/8d48e3bbb2da2f5eb5f4a95efd6846e9ea93a160.patch new file mode 100644 index 0000000..043b78e --- /dev/null +++ b/patches/8d48e3bbb2da2f5eb5f4a95efd6846e9ea93a160.patch @@ -0,0 +1,1958 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 16c18d6..f392e3c 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,6 +1,7 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DEFAULT_BUF_SIZE}; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -42,7 +43,6 @@ use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DE + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -66,7 +66,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -87,7 +86,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -117,7 +115,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -140,7 +137,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -168,7 +164,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -191,7 +186,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -215,7 +209,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -233,7 +226,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -253,7 +245,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -295,7 +286,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -315,7 +305,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -328,7 +317,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index 067ed6b..47869a7 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,7 +1,8 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -63,7 +64,6 @@ use crate::io::{ + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -85,7 +85,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -103,7 +102,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -198,7 +196,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -218,7 +215,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -236,7 +232,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -256,7 +251,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -280,7 +274,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -289,7 +282,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -353,7 +345,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -366,7 +357,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -377,7 +367,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index a80d08d..20bd401 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index f9caeaf..c21de5c 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,28 +119,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/cursor.rs b/cursor.rs +index 5733735..0fdd84a 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,7 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -111,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -129,7 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -150,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -196,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -242,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -271,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -282,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -323,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -351,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -363,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -386,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -407,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -428,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 6642610..efbe402 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -230,7 +236,6 @@ impl Write for dyn ::realstd::io::LocalOutput { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -293,6 +298,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -302,7 +308,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -320,7 +326,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -366,7 +371,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index e6efe6e..e647c6b 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -247,57 +247,46 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print, LocalOutput}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-pub(crate) use self::stdio::clone_io; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + +-mod buffered; ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -324,6 +313,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -351,10 +341,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -488,7 +480,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -559,7 +550,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -571,7 +561,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -584,7 +573,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -608,7 +596,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -660,7 +647,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -703,7 +690,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -767,7 +754,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -821,7 +807,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -858,7 +843,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -896,7 +880,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -935,7 +918,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -944,22 +926,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -972,10 +996,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1010,7 +1033,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1034,7 +1056,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1044,7 +1065,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1057,18 +1077,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1081,10 +1097,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1118,7 +1133,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1142,7 +1156,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1153,13 +1166,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1173,21 +1184,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1241,7 +1249,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1288,7 +1295,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1301,7 +1307,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1316,7 +1321,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1344,7 +1348,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1378,7 +1381,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1440,7 +1442,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1493,7 +1494,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1549,7 +1549,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1584,7 +1583,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1598,7 +1596,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1635,7 +1632,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1673,7 +1669,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1683,29 +1678,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1781,7 +1773,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1822,7 +1814,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1844,7 +1835,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1901,7 +1891,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1964,7 +1953,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2003,7 +1991,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2040,7 +2027,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2055,7 +2041,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2081,7 +2066,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2104,7 +2088,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2131,20 +2114,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2172,7 +2152,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2197,7 +2177,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2230,7 +2209,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2258,7 +2236,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2283,7 +2260,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2308,7 +2284,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2337,13 +2312,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2361,6 +2334,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2369,7 +2343,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2396,13 +2370,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2426,14 +2398,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2458,13 +2430,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index dc05b96..aa7ee35 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,9 +3,10 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -45,7 +46,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -81,7 +81,6 @@ where + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -101,12 +100,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -118,7 +115,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -128,7 +126,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -139,7 +136,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -158,12 +154,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -193,7 +187,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -204,7 +197,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -225,12 +217,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -254,7 +244,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -278,7 +267,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/92bc35f7b6cb4232be5ac4cc031202c7ad82260b.patch b/patches/92bc35f7b6cb4232be5ac4cc031202c7ad82260b.patch new file mode 100644 index 0000000..5b03ccc --- /dev/null +++ b/patches/92bc35f7b6cb4232be5ac4cc031202c7ad82260b.patch @@ -0,0 +1,1817 @@ +diff --git a/buffered.rs b/buffered.rs +index 8e81b29..b042f36 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -216,7 +209,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -236,7 +228,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -274,7 +265,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -294,7 +284,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -307,7 +296,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -418,7 +406,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -453,7 +440,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -468,7 +454,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -486,7 +471,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -533,7 +517,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -553,7 +536,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -571,7 +553,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -595,7 +576,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -604,7 +584,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -640,7 +619,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -653,7 +631,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -663,7 +640,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -702,7 +678,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -737,27 +712,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -828,7 +793,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -849,7 +813,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -870,7 +833,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -891,7 +853,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -916,7 +877,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -944,7 +904,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -952,7 +911,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -996,7 +954,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index a94176e..7768d39 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Initializer, SeekFrom, Error, ErrorKind, IoSlice, IoSliceMut}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { self.inner } + + /// Gets a reference to the underlying value in this cursor. +@@ -128,7 +125,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { &self.inner } + + /// Gets a mutable reference to the underlying value in this cursor. +@@ -147,7 +143,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { &mut self.inner } + + /// Returns the current position of this cursor. +@@ -169,7 +164,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { self.pos } + + /// Sets the position of this cursor. +@@ -189,11 +183,9 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { self.pos = pos; } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor where T: AsRef<[u8]> { + fn seek(&mut self, style: SeekFrom) -> io::Result { + let (base_pos, offset) = match style { +@@ -222,10 +214,9 @@ impl io::Seek for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor where T: AsRef<[u8]> { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -244,7 +235,7 @@ impl Read for Cursor where T: AsRef<[u8]> { + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -255,12 +246,16 @@ impl Read for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor where T: AsRef<[u8]> { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++impl Cursor where T: AsRef<[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor where T: AsRef<[u8]> { ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { self.get_buf() } + fn consume(&mut self, amt: usize) { self.pos += amt as u64; } + } + +@@ -292,6 +287,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new(ErrorKind::InvalidInput, +@@ -318,6 +314,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -331,7 +328,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -347,7 +343,7 @@ impl Write for Cursor<&mut [u8]> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -361,7 +357,7 @@ impl Write for Cursor<&mut Vec> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -375,8 +371,8 @@ impl Write for Cursor> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index c20bd30..99af4d1 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -434,12 +398,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -468,8 +431,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -495,10 +457,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -511,8 +472,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -520,13 +479,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -534,33 +491,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index b7f82e6..c857f83 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -25,11 +29,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -40,7 +46,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -67,14 +72,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -97,7 +101,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -114,11 +118,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -129,7 +135,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -156,14 +162,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -207,7 +213,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -265,6 +270,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -274,7 +280,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -292,7 +298,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -333,7 +338,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index a1a33ba..04bc734 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,53 +257,43 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "0")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -330,6 +320,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -357,10 +348,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -496,7 +489,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -564,7 +556,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -575,7 +566,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -602,7 +592,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -655,7 +644,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -698,7 +687,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -761,7 +750,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -815,7 +803,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -857,7 +844,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -895,7 +881,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -934,7 +919,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -943,16 +927,59 @@ pub trait Read { + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -965,10 +992,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1003,7 +1029,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1027,7 +1052,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1037,7 +1061,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1050,11 +1073,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1067,10 +1088,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1104,7 +1124,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1128,7 +1147,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1139,13 +1157,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1159,21 +1175,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1227,7 +1240,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1276,7 +1288,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1287,7 +1298,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1315,7 +1325,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1348,7 +1357,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1401,7 +1409,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1457,7 +1464,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1492,7 +1498,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1508,7 +1513,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1546,7 +1550,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1585,7 +1588,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1597,29 +1599,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1698,7 +1697,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1739,7 +1738,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1761,7 +1759,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1817,7 +1814,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1876,7 +1872,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1917,7 +1912,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -1959,7 +1953,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -1974,7 +1967,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2000,7 +1992,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2023,7 +2014,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2050,20 +2040,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2091,7 +2078,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2116,7 +2103,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2151,7 +2137,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2179,7 +2164,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2204,7 +2188,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2229,7 +2212,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2258,13 +2240,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2282,6 +2262,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2290,7 +2271,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2317,13 +2298,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2347,14 +2326,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2379,13 +2358,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b09161b..e52119e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -185,7 +179,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -217,12 +209,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -241,7 +231,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/9abd746a327320048ae2b212f34edcadbcafcadf.patch b/patches/9abd746a327320048ae2b212f34edcadbcafcadf.patch new file mode 100644 index 0000000..7a118fa --- /dev/null +++ b/patches/9abd746a327320048ae2b212f34edcadbcafcadf.patch @@ -0,0 +1,2060 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 8bae3da..c6a45f8 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,6 +1,7 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DEFAULT_BUF_SIZE}; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -42,7 +43,6 @@ use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DE + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -66,7 +66,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -87,7 +86,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -117,7 +115,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -140,7 +137,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -168,7 +164,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -191,7 +186,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -215,7 +209,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -233,7 +226,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -253,7 +245,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -309,7 +300,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -329,7 +319,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -342,7 +331,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index fa7bd0d..061c4c9 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,9 +1,9 @@ +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; +-use crate::mem; ++use core::mem; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -65,7 +65,6 @@ use crate::mem; + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -87,7 +86,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -105,7 +103,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -200,7 +197,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -220,7 +216,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -238,7 +233,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -258,7 +252,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -282,7 +275,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -313,7 +305,6 @@ impl BufWriter { + /// assert_eq!(recovered_writer.len(), 0); + /// assert_eq!(&buffered_data.unwrap(), b"ata"); + /// ``` +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_raw_parts(mut self) -> (W, Result, WriterPanicked>) { + let buf = mem::take(&mut self.buf); + let buf = if !self.panicked { Ok(buf) } else { Err(WriterPanicked { buf }) }; +@@ -321,7 +312,6 @@ impl BufWriter { + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + /// Error returned for the buffered data from `BufWriter::into_raw_parts`, when the underlying + /// writer has previously panicked. Contains the (possibly partly written) buffered data. + /// +@@ -355,7 +345,6 @@ pub struct WriterPanicked { + impl WriterPanicked { + /// Returns the perhaps-unwritten data. Some of this data may have been written by the + /// panicking call(s) to the underlying writer, so simply writing it again is not a good idea. +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_inner(self) -> Vec { + self.buf + } +@@ -364,22 +353,12 @@ impl WriterPanicked { + "BufWriter inner writer panicked, what data remains unwritten is not known"; + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] +-impl error::Error for WriterPanicked { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- Self::DESCRIPTION +- } +-} +- +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Display for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + write!(f, "{}", Self::DESCRIPTION) + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Debug for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("WriterPanicked") +@@ -388,7 +367,6 @@ impl fmt::Debug for WriterPanicked { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -485,7 +463,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -498,7 +475,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -509,7 +485,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index d0c859d..a052adf 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index 6549781..0dc7440 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,7 +119,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } +@@ -143,7 +139,6 @@ impl IntoInnerError { + /// let err = into_inner_err.into_error(); + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_error(self) -> Error { + self.1 + } +@@ -167,28 +162,17 @@ impl IntoInnerError { + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// assert_eq!(recovered_writer.buffer(), b"t be actually written"); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_parts(self) -> (Error, W) { + (self.1, self.0) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/copy.rs b/copy.rs +index b88bca2..7593702 100644 +--- a/copy.rs ++++ b/copy.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, ErrorKind, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,19 +39,12 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, + W: Write, + { +- cfg_if::cfg_if! { +- if #[cfg(any(target_os = "linux", target_os = "android"))] { +- crate::sys::kernel_copy::copy_spec(reader, writer) +- } else { +- generic_copy(reader, writer) +- } +- } ++ generic_copy(reader, writer) + } + + /// The general read-write-loop implementation of +diff --git a/cursor.rs b/cursor.rs +index bbee2cc..dc75216 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,8 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,8 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn get_ref(&self) -> &T { + &self.inner + } +@@ -152,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -176,8 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn position(&self) -> u64 { + self.pos + } +@@ -199,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -245,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -274,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -285,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -326,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -354,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -366,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -389,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -410,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -431,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 00bf8b9..5c0e7cd 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -216,7 +222,6 @@ impl BufRead for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -279,6 +284,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -288,7 +294,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -310,7 +316,6 @@ impl BufRead for &[u8] { + /// If the number of bytes to be written exceeds the size of the slice, write operations will + /// return short writes: ultimately, `Ok(0)`; in this situation, `write_all` returns an error of + /// kind `ErrorKind::WriteZero`. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -356,7 +361,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index c87a565..138fcf7 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -246,58 +246,48 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::copy::copy; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[unstable(feature = "internal_output_capture", issue = "none")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::set_output_capture; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + pub(crate) mod copy; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -324,6 +314,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -351,10 +342,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -505,7 +498,6 @@ pub(crate) fn default_read_exact(this: &mut R, mut buf: &mut [ + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -576,7 +568,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -588,7 +579,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -601,7 +591,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -625,7 +614,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -677,7 +665,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -720,7 +708,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -784,7 +772,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, buf: &mut [u8]) -> Result<()> { + default_read_exact(self, buf) + } +@@ -823,7 +810,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -860,7 +846,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -898,7 +883,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -937,7 +921,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -987,29 +970,71 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +-#[unstable(feature = "io_read_to_string", issue = "80218")] ++#[cfg(feature="collections")] + pub fn read_to_string(reader: &mut R) -> Result { + let mut buf = String::new(); + reader.read_to_string(&mut buf)?; + Ok(buf) + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1022,10 +1047,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1060,7 +1084,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1084,7 +1107,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1094,7 +1116,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1107,18 +1128,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1131,10 +1148,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1168,7 +1184,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1192,7 +1207,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1203,13 +1217,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1223,21 +1235,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1291,7 +1300,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1338,7 +1346,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1351,7 +1358,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1366,7 +1372,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1394,7 +1399,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1428,7 +1432,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1490,7 +1493,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1543,7 +1545,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1599,7 +1600,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1634,7 +1634,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1648,7 +1647,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1685,7 +1683,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1723,7 +1720,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1733,29 +1729,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1831,7 +1824,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1872,7 +1865,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1894,7 +1886,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1951,7 +1942,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -2014,7 +2004,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2052,7 +2041,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2089,7 +2077,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2104,7 +2091,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2130,7 +2116,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2153,7 +2138,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2180,20 +2164,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2221,7 +2202,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2246,7 +2227,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2279,7 +2259,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2307,7 +2286,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2332,7 +2310,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2357,7 +2334,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2386,13 +2362,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2410,6 +2384,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2418,7 +2393,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2445,13 +2420,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2475,14 +2448,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2507,13 +2480,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index d806431..6b9791a 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index db84545..8e88c3d 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,14 +3,14 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, Initializer, IoSlice, IoSliceMut, Read, Write}; ++use core::fmt; ++use crate::io::{self, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; + + /// A reader which is always at EOF. + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -30,13 +30,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -48,7 +45,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -58,7 +56,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -69,7 +66,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -88,13 +84,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -124,7 +117,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -135,7 +127,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -156,13 +147,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -186,7 +174,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -210,7 +197,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/9bb2a50e04460fff646830502d575b82dbf17055.patch b/patches/9bb2a50e04460fff646830502d575b82dbf17055.patch new file mode 100644 index 0000000..91d0a07 --- /dev/null +++ b/patches/9bb2a50e04460fff646830502d575b82dbf17055.patch @@ -0,0 +1,1832 @@ +diff --git a/buffered.rs b/buffered.rs +index 9e6849b..7021de4 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -216,7 +209,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -236,7 +228,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -274,7 +265,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -294,7 +284,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -307,7 +296,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -418,7 +406,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -453,7 +440,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -468,7 +454,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -486,7 +471,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -533,7 +517,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -553,7 +536,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -571,7 +553,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -595,7 +576,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -604,7 +584,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -640,7 +619,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -653,7 +631,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -663,7 +640,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -702,7 +678,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -737,28 +712,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -829,7 +793,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -850,7 +813,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -871,7 +833,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -892,7 +853,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -917,7 +877,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -945,7 +904,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -953,7 +911,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1059,7 +1016,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index 9787cbb..1cf83d3 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -268,7 +259,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -279,15 +270,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -320,6 +320,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -348,6 +349,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -360,7 +362,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -378,7 +379,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -394,7 +395,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -410,8 +411,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index 3b55d9b..c754d1f 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -432,12 +396,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -466,8 +429,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -493,10 +455,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -509,8 +470,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -518,13 +477,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -532,34 +489,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index b7f82e6..c857f83 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -25,11 +29,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -40,7 +46,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -67,14 +72,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -97,7 +101,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -114,11 +118,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -129,7 +135,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -156,14 +162,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -207,7 +213,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -265,6 +270,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -274,7 +280,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -292,7 +298,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -333,7 +338,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 67b382c..f8ccb5e 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,53 +257,43 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -330,6 +320,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -357,10 +348,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -496,7 +489,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -564,7 +556,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -575,7 +566,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -602,7 +592,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -655,7 +644,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -698,7 +687,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -761,7 +750,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -815,7 +803,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -857,7 +844,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -895,7 +881,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -934,7 +919,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -943,16 +927,59 @@ pub trait Read { + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -965,10 +992,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1003,7 +1029,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1027,7 +1052,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1037,7 +1061,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1050,11 +1073,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1067,10 +1088,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1104,7 +1124,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1128,7 +1147,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1139,13 +1157,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1159,21 +1175,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1227,7 +1240,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1276,7 +1288,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1287,7 +1298,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1315,7 +1325,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1350,7 +1359,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1403,7 +1411,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1459,7 +1466,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1494,7 +1500,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1510,7 +1515,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1548,7 +1552,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1587,7 +1590,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1599,29 +1601,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1700,7 +1699,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1741,7 +1740,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1763,7 +1761,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1819,7 +1816,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1878,7 +1874,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1919,7 +1914,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -1961,7 +1955,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -1976,7 +1969,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2002,7 +1994,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2025,7 +2016,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2052,20 +2042,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2093,7 +2080,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2118,7 +2105,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2153,7 +2139,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2181,7 +2166,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2206,7 +2190,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2231,7 +2214,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2260,13 +2242,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2284,6 +2264,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2292,7 +2273,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2319,13 +2300,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2349,14 +2328,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2381,13 +2360,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b09161b..e52119e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -185,7 +179,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -217,12 +209,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -241,7 +231,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/9fe551ae49289ce6f693ca0dabf4c9c15164f67d.patch b/patches/9fe551ae49289ce6f693ca0dabf4c9c15164f67d.patch new file mode 100644 index 0000000..8905c3a --- /dev/null +++ b/patches/9fe551ae49289ce6f693ca0dabf4c9c15164f67d.patch @@ -0,0 +1,1903 @@ +diff --git a/buffered.rs b/buffered.rs +index 97c4b87..ae26453 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -3,15 +3,15 @@ + #[cfg(test)] + mod tests; + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -52,7 +52,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -76,7 +75,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -97,7 +95,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -127,7 +124,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -150,7 +146,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -178,7 +173,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -201,7 +195,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -225,7 +218,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -243,7 +235,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -263,7 +254,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -305,7 +295,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -325,7 +314,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -338,7 +326,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -492,7 +479,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: Write::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: Write::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -527,7 +513,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -542,7 +527,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -560,7 +544,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -655,7 +638,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -675,7 +657,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -693,7 +674,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -713,7 +693,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -737,7 +716,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -746,7 +724,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -810,7 +787,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -823,7 +799,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -834,7 +809,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -874,7 +848,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -909,28 +882,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -1267,7 +1229,6 @@ impl<'a, W: Write> Write for LineWriterShim<'a, W> { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -1287,7 +1248,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -1308,7 +1268,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -1329,7 +1288,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -1354,7 +1312,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -1382,7 +1339,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner + .into_inner() +@@ -1390,7 +1346,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -1421,7 +1376,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index 5733735..0fdd84a 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,7 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -111,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -129,7 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -150,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -196,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -242,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -271,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -282,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -323,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -351,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -363,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -386,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -407,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -428,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index e09e7ba..126a710 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -230,7 +236,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -293,6 +298,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -302,7 +308,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -320,7 +326,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -366,7 +371,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index adea8a8..e647c6b 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -247,56 +247,46 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -323,6 +313,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -350,10 +341,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -487,7 +480,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -558,7 +550,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -570,7 +561,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -583,7 +573,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -607,7 +596,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -659,7 +647,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -702,7 +690,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -766,7 +754,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -820,7 +807,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -857,7 +843,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -895,7 +880,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -934,7 +918,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -943,22 +926,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -971,10 +996,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1009,7 +1033,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1033,7 +1056,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1043,7 +1065,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1056,18 +1077,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1080,10 +1097,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1117,7 +1133,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1141,7 +1156,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1152,13 +1166,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1172,21 +1184,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1240,7 +1249,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1287,7 +1295,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1300,7 +1307,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1315,7 +1321,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1343,7 +1348,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1377,7 +1381,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1439,7 +1442,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1492,7 +1494,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1548,7 +1549,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1583,7 +1583,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1597,7 +1596,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1634,7 +1632,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1672,7 +1669,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1682,29 +1678,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1780,7 +1773,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1821,7 +1814,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1843,7 +1835,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1900,7 +1891,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1963,7 +1953,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2002,7 +1991,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2039,7 +2027,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2054,7 +2041,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2080,7 +2066,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2103,7 +2088,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2130,20 +2114,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2171,7 +2152,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2196,7 +2177,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2229,7 +2209,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2257,7 +2236,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2282,7 +2260,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2307,7 +2284,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2336,13 +2312,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2360,6 +2334,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2368,7 +2343,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2395,13 +2370,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2425,14 +2398,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2457,13 +2430,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index 44d2937..a7d9389 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,9 +3,10 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -45,7 +46,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -81,7 +81,6 @@ where + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -101,12 +100,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -118,7 +115,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -128,7 +126,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -139,7 +136,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -158,12 +154,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -193,7 +187,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -204,7 +197,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -225,12 +217,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -254,7 +244,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/9ff52752d855722c55dbc71d9b22bd42eabfc468.patch b/patches/9ff52752d855722c55dbc71d9b22bd42eabfc468.patch new file mode 100644 index 0000000..618fc11 --- /dev/null +++ b/patches/9ff52752d855722c55dbc71d9b22bd42eabfc468.patch @@ -0,0 +1,1761 @@ +diff --git a/buffered.rs b/buffered.rs +index aaf628e..259eba3 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,13 +1,13 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, Initializer, DEFAULT_BUF_SIZE, Error, ErrorKind, SeekFrom, IoSlice, + IoSliceMut}; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -47,7 +47,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -71,7 +70,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -92,7 +90,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -127,7 +124,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { &self.inner } + + /// Gets a mutable reference to the underlying reader. +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { &mut self.inner } + + /// Returns a reference to the internally buffered data. +@@ -172,7 +167,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -195,7 +189,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { self.inner } + + /// Invalidates all data in the internal buffer. +@@ -211,7 +204,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -231,7 +223,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -269,7 +260,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -289,7 +279,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader where R: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufReader") +@@ -299,7 +288,6 @@ impl fmt::Debug for BufReader where R: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -408,7 +396,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -443,7 +430,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -458,7 +444,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -476,7 +461,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { + inner: Some(inner), +@@ -525,7 +509,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.as_ref().unwrap() } + + /// Gets a mutable reference to the underlying writer. +@@ -543,7 +526,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.as_mut().unwrap() } + + /// Returns a reference to the internally buffered data. +@@ -559,7 +541,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -583,7 +564,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -592,7 +572,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -628,7 +607,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufWriter") +@@ -638,7 +616,6 @@ impl fmt::Debug for BufWriter where W: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -648,7 +625,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -687,7 +663,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { &self.1 } + + /// Returns the buffered writer instance which generated the error. +@@ -720,23 +695,13 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { self.0 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { iie.1 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -807,7 +772,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -828,7 +792,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -849,7 +812,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { + inner: BufWriter::with_capacity(capacity, inner), +@@ -873,7 +835,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.get_ref() } + + /// Gets a mutable reference to the underlying writer. +@@ -896,7 +857,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.get_mut() } + + /// Unwraps this `LineWriter`, returning the underlying writer. +@@ -922,7 +882,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { +@@ -933,7 +892,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -978,7 +936,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("LineWriter") +diff --git a/cursor.rs b/cursor.rs +index a94176e..7768d39 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Initializer, SeekFrom, Error, ErrorKind, IoSlice, IoSliceMut}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { self.inner } + + /// Gets a reference to the underlying value in this cursor. +@@ -128,7 +125,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { &self.inner } + + /// Gets a mutable reference to the underlying value in this cursor. +@@ -147,7 +143,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { &mut self.inner } + + /// Returns the current position of this cursor. +@@ -169,7 +164,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { self.pos } + + /// Sets the position of this cursor. +@@ -189,11 +183,9 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { self.pos = pos; } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor where T: AsRef<[u8]> { + fn seek(&mut self, style: SeekFrom) -> io::Result { + let (base_pos, offset) = match style { +@@ -222,10 +214,9 @@ impl io::Seek for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor where T: AsRef<[u8]> { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -244,7 +235,7 @@ impl Read for Cursor where T: AsRef<[u8]> { + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -255,12 +246,16 @@ impl Read for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor where T: AsRef<[u8]> { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++impl Cursor where T: AsRef<[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor where T: AsRef<[u8]> { ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { self.get_buf() } + fn consume(&mut self, amt: usize) { self.pos += amt as u64; } + } + +@@ -292,6 +287,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new(ErrorKind::InvalidInput, +@@ -318,6 +314,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -331,7 +328,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -347,7 +343,7 @@ impl Write for Cursor<&mut [u8]> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -361,7 +357,7 @@ impl Write for Cursor<&mut Vec> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -375,8 +371,8 @@ impl Write for Cursor> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index c29a68e..c94d8c5 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,13 @@ +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; +-use crate::convert::From; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++use core::convert::Into; ++use core::fmt; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++use core::result; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; ++use core::convert::From; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +43,6 @@ use crate::convert::From; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +56,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +69,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +90,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +130,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +142,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +156,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +186,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -245,14 +230,13 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error +- where E: Into> ++ where E: Into + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { + repr: Repr::Custom(Box::new(Custom { + kind, +@@ -261,24 +245,6 @@ impl Error { + } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -304,7 +270,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -335,7 +300,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -369,12 +333,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error+Send+Sync+'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -440,12 +403,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error+Send+Sync+'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -474,8 +436,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -501,10 +462,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -516,22 +476,18 @@ impl fmt::Debug for Repr { + match *self { + Repr::Os(code) => + fmt.debug_struct("Os") +- .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)).finish(), ++ .field("code", &code).finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), + } + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -539,33 +495,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index c959f2d..b645bc8 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,13 +1,15 @@ +-use crate::cmp; +-use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, BufRead, Error, ErrorKind, +- IoSliceMut, IoSlice}; +-use crate::fmt; +-use crate::mem; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++use core::cmp; ++use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, Error, ErrorKind, IoSliceMut, IoSlice}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::fmt; ++use core::mem; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -24,11 +26,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -39,7 +43,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -62,12 +65,11 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -86,7 +88,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -103,11 +105,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -118,7 +122,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -141,12 +145,12 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -186,7 +190,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -245,6 +248,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -254,7 +258,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(*self) } +@@ -268,7 +272,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -307,7 +310,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index f89a714..3f95d8e 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,50 +257,38 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::slice; +-use crate::str; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(feature="collections")] use collections::string::String; ++use core::str; ++#[cfg(feature="collections")] use collections::vec::Vec; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::slice; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++ ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Result, Error, ErrorKind}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, sink, Sink, empty, Empty, repeat, Repeat}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stdin, stdout, stderr, Stdin, Stdout, Stderr}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StdoutLock, StderrLock, StdinLock}; +-#[unstable(feature = "print_internals", issue = "0")] +-pub use self::stdio::{_print, _eprint}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; + + pub mod prelude; +-mod buffered; ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + mod util; +-mod stdio; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { buf: &'a mut Vec, len: usize } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { self.buf.set_len(self.len); } +@@ -325,6 +313,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where F: FnOnce(&mut Vec) -> Result + { +@@ -352,10 +341,12 @@ fn append_to_string(buf: &mut String, f: F) -> Result + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation(r: &mut R, + buf: &mut Vec, + reservation_size: usize) -> Result +@@ -484,7 +475,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -552,7 +542,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -563,7 +552,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -590,7 +578,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -643,7 +630,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -686,7 +673,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -749,7 +736,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -801,7 +787,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + + /// Transforms this `Read` instance to an [`Iterator`] over its bytes. +@@ -838,7 +823,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes where Self: Sized { + Bytes { inner: self } + } +@@ -873,7 +857,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain where Self: Sized { + Chain { first: self, second: next, done_first: false } + } +@@ -909,22 +892,52 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take where Self: Sized { + Take { inner: self, limit: limit } + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -937,14 +950,12 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -954,7 +965,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -967,11 +977,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -984,14 +992,12 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1002,13 +1008,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1022,21 +1026,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1090,7 +1091,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1139,7 +1139,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1150,7 +1149,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1178,7 +1176,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1211,7 +1208,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1263,7 +1259,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1319,7 +1314,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + } + +@@ -1349,7 +1343,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1365,7 +1358,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1403,7 +1395,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1442,7 +1433,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1454,29 +1444,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + -> Result { + let mut read = 0; +@@ -1556,7 +1543,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1597,7 +1584,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1619,7 +1605,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1675,7 +1660,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1734,7 +1718,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1775,7 +1758,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split where Self: Sized { + Split { buf: self, delim: byte } + } +@@ -1814,7 +1796,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines where Self: Sized { + Lines { buf: self } + } +@@ -1826,7 +1807,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -1852,7 +1832,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -1875,7 +1854,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -1902,13 +1880,11 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain") +@@ -1918,7 +1894,6 @@ impl fmt::Debug for Chain { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -1950,7 +1925,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -1977,7 +1952,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2012,7 +1986,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { self.limit } + + /// Sets the number of bytes that can be read before this instance will +@@ -2038,7 +2011,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2063,7 +2035,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2088,7 +2059,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2117,13 +2087,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2141,6 +2109,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + let reservation_size = cmp::min(self.limit, 32) as usize; + +@@ -2148,7 +2117,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2175,13 +2144,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2205,14 +2172,14 @@ impl Iterator for Bytes { + /// `BufRead`. Please see the documentation of `split()` for more details. + /// + /// [split]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2237,13 +2204,13 @@ impl Iterator for Split { + /// `BufRead`. Please see the documentation of `lines()` for more details. + /// + /// [lines]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 2e19edf..66294a3 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Write, Seek}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{Read, Write, BufRead, Seek}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index 33cc87e..75b8032 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, Read, Initializer, Write, ErrorKind, BufRead, IoSlice, IoSliceMut}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, Read, Initializer, Write, ErrorKind, IoSlice, IoSliceMut}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where R: Read, W: Write + { +@@ -70,7 +70,6 @@ pub fn copy(reader: &mut R, writer: &mut W) -> io::Result< + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { _priv: () } + + /// Constructs a new handle to an empty reader. +@@ -90,10 +89,8 @@ pub struct Empty { _priv: () } + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { Empty { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { Ok(0) } +@@ -103,7 +100,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(&[]) } +@@ -111,7 +109,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -124,7 +121,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { byte: u8 } + + /// Creates an instance of a reader that infinitely repeats one byte. +@@ -141,10 +137,8 @@ pub struct Repeat { byte: u8 } + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { Repeat { byte } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -169,7 +163,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -182,7 +175,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { _priv: () } + + /// Creates an instance of a writer which will successfully consume all data. +@@ -199,10 +191,8 @@ pub struct Sink { _priv: () } + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { Sink { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { Ok(buf.len()) } +@@ -217,7 +207,6 @@ impl Write for Sink { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/a42e62fa0a59d0ba620889f97513929a113a6fbd.patch b/patches/a42e62fa0a59d0ba620889f97513929a113a6fbd.patch new file mode 100644 index 0000000..6021547 --- /dev/null +++ b/patches/a42e62fa0a59d0ba620889f97513929a113a6fbd.patch @@ -0,0 +1,2093 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 02b0fc0..fe6e4af 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,8 +1,9 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, SizeHint, DEFAULT_BUF_SIZE, + }; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -44,7 +45,6 @@ use crate::io::{ + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -68,7 +68,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -89,7 +88,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buf = Box::new_uninit_slice(capacity).assume_init(); +@@ -118,7 +116,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -141,7 +138,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -169,7 +165,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -192,7 +187,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -216,7 +210,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -234,7 +227,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -254,7 +246,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -310,7 +301,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -330,7 +320,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -343,7 +332,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index 80f98bb..d11d026 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,9 +1,9 @@ +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; +-use crate::mem; ++use core::mem; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -65,7 +65,6 @@ use crate::mem; + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -87,7 +86,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -105,7 +103,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -200,7 +197,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -220,7 +216,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -238,7 +233,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -270,7 +264,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -294,7 +287,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -325,7 +317,6 @@ impl BufWriter { + /// assert_eq!(recovered_writer.len(), 0); + /// assert_eq!(&buffered_data.unwrap(), b"ata"); + /// ``` +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_raw_parts(mut self) -> (W, Result, WriterPanicked>) { + let buf = mem::take(&mut self.buf); + let buf = if !self.panicked { Ok(buf) } else { Err(WriterPanicked { buf }) }; +@@ -333,7 +324,6 @@ impl BufWriter { + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + /// Error returned for the buffered data from `BufWriter::into_raw_parts`, when the underlying + /// writer has previously panicked. Contains the (possibly partly written) buffered data. + /// +@@ -367,7 +357,6 @@ pub struct WriterPanicked { + impl WriterPanicked { + /// Returns the perhaps-unwritten data. Some of this data may have been written by the + /// panicking call(s) to the underlying writer, so simply writing it again is not a good idea. +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_inner(self) -> Vec { + self.buf + } +@@ -376,22 +365,12 @@ impl WriterPanicked { + "BufWriter inner writer panicked, what data remains unwritten is not known"; + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] +-impl error::Error for WriterPanicked { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- Self::DESCRIPTION +- } +-} +- +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Display for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + write!(f, "{}", Self::DESCRIPTION) + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Debug for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("WriterPanicked") +@@ -400,7 +379,6 @@ impl fmt::Debug for WriterPanicked { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -497,7 +475,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -510,7 +487,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -521,7 +497,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index d0c859d..a052adf 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index 6549781..0dc7440 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,7 +119,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } +@@ -143,7 +139,6 @@ impl IntoInnerError { + /// let err = into_inner_err.into_error(); + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_error(self) -> Error { + self.1 + } +@@ -167,28 +162,17 @@ impl IntoInnerError { + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// assert_eq!(recovered_writer.buffer(), b"t be actually written"); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_parts(self) -> (Error, W) { + (self.1, self.0) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/copy.rs b/copy.rs +index eb60df2..df99a47 100644 +--- a/copy.rs ++++ b/copy.rs +@@ -1,5 +1,6 @@ +-use super::{BufWriter, ErrorKind, Read, Result, Write, DEFAULT_BUF_SIZE}; +-use crate::mem::MaybeUninit; ++use super::{ErrorKind, Read, Result, Write, DEFAULT_BUF_SIZE}; ++#[cfg(feature = "collections")] use super::BufWriter; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,19 +40,12 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> Result + where + R: Read, + W: Write, + { +- cfg_if::cfg_if! { +- if #[cfg(any(target_os = "linux", target_os = "android"))] { +- crate::sys::kernel_copy::copy_spec(reader, writer) +- } else { +- generic_copy(reader, writer) +- } +- } ++ generic_copy(reader, writer) + } + + /// The userspace read-write-loop implementation of `io::copy` that is used when +@@ -76,6 +70,7 @@ impl BufferedCopySpec for W { + } + } + ++#[cfg(feature = "collections")] + impl BufferedCopySpec for BufWriter { + fn copy_to(reader: &mut R, writer: &mut Self) -> Result { + if writer.capacity() < DEFAULT_BUF_SIZE { +diff --git a/cursor.rs b/cursor.rs +index 9021b47..49ebb05 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,8 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,8 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn get_ref(&self) -> &T { + &self.inner + } +@@ -152,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -176,8 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn position(&self) -> u64 { + self.pos + } +@@ -199,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -245,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -274,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -285,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -326,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new_const( +@@ -354,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -366,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -389,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -410,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -431,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index 2122aa7..5bba143 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -71,13 +74,16 @@ enum Repr { + Simple(ErrorKind), + // &str is a fat pointer, but &&str is a thin pointer. + SimpleMessage(ErrorKind, &'static &'static str), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -89,48 +95,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -142,10 +135,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -156,12 +147,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -169,7 +158,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -178,7 +166,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -209,7 +196,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -249,15 +235,14 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +@@ -273,24 +258,6 @@ impl Error { + Self { repr: Repr::SimpleMessage(kind, message) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -316,7 +283,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -350,7 +316,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -387,13 +352,12 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, + Repr::SimpleMessage(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -459,13 +423,12 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, + Repr::SimpleMessage(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -496,8 +459,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -524,10 +486,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + Repr::SimpleMessage(kind, _) => kind, +@@ -541,8 +502,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -553,13 +512,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -568,37 +525,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::SimpleMessage(_, &msg) => msg, +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::SimpleMessage(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::SimpleMessage(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 6891bd8..22b2b02 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,18 +1,22 @@ + #[cfg(test)] + mod tests; + +-use crate::alloc::Allocator; +-use crate::cmp; +-use crate::fmt; ++#[cfg(feature="collections")] use core::alloc::Allocator; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -34,11 +38,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -49,7 +55,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -81,14 +86,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -111,7 +115,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -133,11 +137,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -148,7 +154,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -180,14 +186,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -217,7 +223,6 @@ impl BufRead for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -280,6 +285,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -289,7 +295,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -311,7 +317,6 @@ impl BufRead for &[u8] { + /// If the number of bytes to be written exceeds the size of the slice, write operations will + /// return short writes: ultimately, `Ok(0)`; in this situation, `write_all` returns an error of + /// kind `ErrorKind::WriteZero`. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -357,7 +362,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 5316305..cbd6af2 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -246,58 +246,48 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::copy::copy; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[unstable(feature = "internal_output_capture", issue = "none")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::set_output_capture; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + pub(crate) mod copy; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -324,6 +314,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -351,10 +342,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -504,7 +497,6 @@ pub(crate) fn default_read_exact(this: &mut R, mut buf: &mut [ + /// [`&str`]: prim@str + /// [`std::io`]: self + /// [`File`]: crate::fs::File +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -580,7 +572,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -592,7 +583,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -605,7 +595,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -629,7 +618,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -681,7 +669,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -724,7 +712,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -788,7 +776,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, buf: &mut [u8]) -> Result<()> { + default_read_exact(self, buf) + } +@@ -827,7 +814,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -864,7 +850,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -902,7 +887,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -941,7 +925,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -991,29 +974,71 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +-#[unstable(feature = "io_read_to_string", issue = "80218")] ++#[cfg(feature="collections")] + pub fn read_to_string(reader: &mut R) -> Result { + let mut buf = String::new(); + reader.read_to_string(&mut buf)?; + Ok(buf) + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1026,10 +1051,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1064,7 +1088,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1088,7 +1111,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1098,7 +1120,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1111,18 +1132,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1135,10 +1152,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1172,7 +1188,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1196,7 +1211,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1207,13 +1221,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1227,21 +1239,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1295,7 +1304,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1342,7 +1350,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1355,7 +1362,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1370,7 +1376,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1398,7 +1403,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1432,7 +1436,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1497,7 +1500,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1553,7 +1555,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1609,7 +1610,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1644,7 +1644,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1658,7 +1657,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1695,7 +1693,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_stream_len", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1732,7 +1729,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "seek_convenience", since = "1.51.0")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1742,29 +1738,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1840,7 +1833,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1881,7 +1874,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1903,7 +1895,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1960,7 +1951,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -2023,7 +2013,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2061,7 +2050,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2098,7 +2086,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2113,7 +2100,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2139,7 +2125,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2162,7 +2147,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2189,20 +2173,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2230,7 +2211,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2268,7 +2249,6 @@ impl SizeHint for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2301,7 +2281,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2329,7 +2308,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2354,7 +2332,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2379,7 +2356,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2408,13 +2384,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2432,6 +2406,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2440,7 +2415,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2467,13 +2442,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2521,14 +2494,14 @@ impl SizeHint for T { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2553,13 +2526,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index d806431..6b9791a 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index f472361..0a1899d 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,16 +3,16 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; ++use core::fmt; + use crate::io::{ +- self, BufRead, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, SizeHint, Write, ++ self, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, SizeHint, Write, + }; ++#[cfg(feature="collections")] use crate::io::BufRead; + + /// A reader which is always at EOF. + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -32,13 +32,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -50,7 +47,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -60,7 +58,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "empty_seek", since = "1.51.0")] + impl Seek for Empty { + fn seek(&mut self, _pos: SeekFrom) -> io::Result { + Ok(0) +@@ -75,7 +72,6 @@ impl Seek for Empty { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -92,7 +88,6 @@ impl SizeHint for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -111,13 +106,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -147,7 +139,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -158,7 +149,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -179,13 +169,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -209,7 +196,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -233,7 +219,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/a7749fe451c37ec192b282ec7303b9809b49df93.patch b/patches/a7749fe451c37ec192b282ec7303b9809b49df93.patch new file mode 100644 index 0000000..90dac14 --- /dev/null +++ b/patches/a7749fe451c37ec192b282ec7303b9809b49df93.patch @@ -0,0 +1,1891 @@ +diff --git a/buffered.rs b/buffered.rs +index b4c91cc..3c3cad2 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -197,7 +191,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -221,7 +214,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -239,7 +231,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -259,7 +250,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -301,7 +291,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -321,7 +310,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -334,7 +322,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -445,7 +432,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -480,7 +466,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -495,7 +480,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -513,7 +497,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -560,7 +543,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -580,7 +562,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -598,7 +579,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -618,7 +598,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -642,7 +621,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -651,7 +629,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -691,7 +668,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -704,7 +680,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -714,7 +689,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -753,7 +727,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -788,28 +761,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -880,7 +842,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -901,7 +862,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -922,7 +882,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -943,7 +902,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -968,7 +926,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -996,7 +953,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -1004,7 +960,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1105,7 +1060,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index f4db5f8..4f20b8a 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -272,7 +263,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -283,15 +274,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -324,6 +324,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -352,6 +353,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -364,7 +366,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -387,7 +388,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -408,7 +409,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -429,8 +430,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index f7248e7..f7311ad 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,12 +143,10 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -165,7 +154,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -174,7 +162,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -205,7 +192,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -248,36 +234,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -303,7 +270,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -334,7 +300,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -368,12 +333,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -437,12 +401,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -471,8 +434,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -498,10 +460,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -514,8 +475,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -523,13 +482,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -537,34 +494,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 01dff0b..eb78a0f 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -30,11 +34,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -45,7 +51,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -77,14 +82,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -107,7 +111,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -129,11 +133,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -144,7 +150,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -176,14 +182,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -227,7 +233,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -290,6 +295,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -299,7 +305,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -317,7 +323,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -363,7 +368,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index e90ee5c..09a607f 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -247,53 +247,43 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -320,6 +310,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -347,10 +338,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -484,7 +477,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -555,7 +547,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -567,7 +558,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -580,7 +570,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -604,7 +593,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -656,7 +644,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -699,7 +687,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -763,7 +751,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -817,7 +804,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -855,7 +841,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -893,7 +878,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -932,7 +916,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -941,22 +924,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -969,10 +994,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1007,7 +1031,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1031,7 +1054,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1041,7 +1063,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1054,18 +1075,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1078,10 +1095,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1115,7 +1131,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1139,7 +1154,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1150,13 +1164,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1170,21 +1182,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1238,7 +1247,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Self::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1283,7 +1291,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1294,7 +1301,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1307,7 +1313,6 @@ pub trait Write { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1335,7 +1340,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1369,7 +1373,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1432,7 +1435,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1485,7 +1487,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1541,7 +1542,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1576,7 +1576,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1590,7 +1589,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1628,7 +1626,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1667,7 +1664,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1677,29 +1673,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1776,7 +1769,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1817,7 +1810,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1839,7 +1831,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: Self::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1896,7 +1887,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1957,7 +1947,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1996,7 +1985,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2033,7 +2021,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2048,7 +2035,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2074,7 +2060,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2097,7 +2082,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2124,20 +2108,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2165,7 +2146,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2190,7 +2171,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2223,7 +2203,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2251,7 +2230,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2276,7 +2254,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2301,7 +2278,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2330,13 +2306,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2354,6 +2328,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2362,7 +2337,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2389,13 +2364,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2419,14 +2392,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2451,13 +2424,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b9d5dc2..07d090e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -190,7 +184,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -203,7 +196,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -222,12 +214,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -251,7 +241,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/a8c5f90b06c9bf2bfa2c2f4aedd7c395cb92195d.patch b/patches/a8c5f90b06c9bf2bfa2c2f4aedd7c395cb92195d.patch new file mode 100644 index 0000000..cc43f5a --- /dev/null +++ b/patches/a8c5f90b06c9bf2bfa2c2f4aedd7c395cb92195d.patch @@ -0,0 +1,1797 @@ +diff --git a/buffered.rs b/buffered.rs +index 9593a1b..0b6c3eb 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,13 +1,13 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, Initializer, DEFAULT_BUF_SIZE, Error, ErrorKind, SeekFrom, IoSlice, + IoSliceMut}; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -47,7 +47,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -71,7 +70,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -92,7 +90,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -127,7 +124,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { &self.inner } + + /// Gets a mutable reference to the underlying reader. +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { &mut self.inner } + + /// Returns a reference to the internally buffered data. +@@ -172,7 +167,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -195,7 +189,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { self.inner } + + /// Invalidates all data in the internal buffer. +@@ -211,7 +204,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -231,7 +223,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -269,7 +260,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -289,7 +279,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader where R: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufReader") +@@ -299,7 +288,6 @@ impl fmt::Debug for BufReader where R: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -410,7 +398,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -445,7 +432,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -460,7 +446,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -478,7 +463,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { + inner: Some(inner), +@@ -527,7 +511,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.as_ref().unwrap() } + + /// Gets a mutable reference to the underlying writer. +@@ -545,7 +528,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.as_mut().unwrap() } + + /// Returns a reference to the internally buffered data. +@@ -561,7 +543,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -585,7 +566,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -594,7 +574,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -630,7 +609,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufWriter") +@@ -640,7 +618,6 @@ impl fmt::Debug for BufWriter where W: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -650,7 +627,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -689,7 +665,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { &self.1 } + + /// Returns the buffered writer instance which generated the error. +@@ -722,23 +697,13 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { self.0 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { iie.1 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -809,7 +774,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -830,7 +794,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -851,7 +814,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { + inner: BufWriter::with_capacity(capacity, inner), +@@ -875,7 +837,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.get_ref() } + + /// Gets a mutable reference to the underlying writer. +@@ -898,7 +859,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.get_mut() } + + /// Unwraps this `LineWriter`, returning the underlying writer. +@@ -924,7 +884,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { +@@ -935,7 +894,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -980,7 +938,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("LineWriter") +diff --git a/cursor.rs b/cursor.rs +index a94176e..7768d39 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Initializer, SeekFrom, Error, ErrorKind, IoSlice, IoSliceMut}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { self.inner } + + /// Gets a reference to the underlying value in this cursor. +@@ -128,7 +125,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { &self.inner } + + /// Gets a mutable reference to the underlying value in this cursor. +@@ -147,7 +143,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { &mut self.inner } + + /// Returns the current position of this cursor. +@@ -169,7 +164,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { self.pos } + + /// Sets the position of this cursor. +@@ -189,11 +183,9 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { self.pos = pos; } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor where T: AsRef<[u8]> { + fn seek(&mut self, style: SeekFrom) -> io::Result { + let (base_pos, offset) = match style { +@@ -222,10 +214,9 @@ impl io::Seek for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor where T: AsRef<[u8]> { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -244,7 +235,7 @@ impl Read for Cursor where T: AsRef<[u8]> { + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -255,12 +246,16 @@ impl Read for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor where T: AsRef<[u8]> { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++impl Cursor where T: AsRef<[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor where T: AsRef<[u8]> { ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { self.get_buf() } + fn consume(&mut self, amt: usize) { self.pos += amt as u64; } + } + +@@ -292,6 +287,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new(ErrorKind::InvalidInput, +@@ -318,6 +314,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -331,7 +328,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -347,7 +343,7 @@ impl Write for Cursor<&mut [u8]> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -361,7 +357,7 @@ impl Write for Cursor<&mut Vec> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -375,8 +371,8 @@ impl Write for Cursor> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index c29a68e..c94d8c5 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,13 @@ +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; +-use crate::convert::From; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++use core::convert::Into; ++use core::fmt; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++use core::result; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; ++use core::convert::From; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +43,6 @@ use crate::convert::From; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +56,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +69,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +90,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +130,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +142,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +156,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +186,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -245,14 +230,13 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error +- where E: Into> ++ where E: Into + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { + repr: Repr::Custom(Box::new(Custom { + kind, +@@ -261,24 +245,6 @@ impl Error { + } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -304,7 +270,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -335,7 +300,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -369,12 +333,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error+Send+Sync+'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -440,12 +403,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error+Send+Sync+'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -474,8 +436,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -501,10 +462,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -516,22 +476,18 @@ impl fmt::Debug for Repr { + match *self { + Repr::Os(code) => + fmt.debug_struct("Os") +- .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)).finish(), ++ .field("code", &code).finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), + } + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -539,33 +495,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index c959f2d..b645bc8 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,13 +1,15 @@ +-use crate::cmp; +-use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, BufRead, Error, ErrorKind, +- IoSliceMut, IoSlice}; +-use crate::fmt; +-use crate::mem; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++use core::cmp; ++use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, Error, ErrorKind, IoSliceMut, IoSlice}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::fmt; ++use core::mem; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -24,11 +26,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -39,7 +43,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -62,12 +65,11 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -86,7 +88,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -103,11 +105,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -118,7 +122,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -141,12 +145,12 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -186,7 +190,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -245,6 +248,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -254,7 +258,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(*self) } +@@ -268,7 +272,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -307,7 +310,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 0386dbd..d7760e0 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,50 +257,38 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::slice; +-use crate::str; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(feature="collections")] use collections::string::String; ++use core::str; ++#[cfg(feature="collections")] use collections::vec::Vec; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::slice; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++ ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Result, Error, ErrorKind}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, sink, Sink, empty, Empty, repeat, Repeat}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stdin, stdout, stderr, Stdin, Stdout, Stderr}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StdoutLock, StderrLock, StdinLock}; +-#[unstable(feature = "print_internals", issue = "0")] +-pub use self::stdio::{_print, _eprint}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; + + pub mod prelude; +-mod buffered; ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + mod util; +-mod stdio; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { buf: &'a mut Vec, len: usize } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { self.buf.set_len(self.len); } +@@ -325,6 +313,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where F: FnOnce(&mut Vec) -> Result + { +@@ -352,10 +341,12 @@ fn append_to_string(buf: &mut String, f: F) -> Result + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -497,7 +488,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -565,7 +555,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -576,7 +565,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -603,7 +591,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -656,7 +643,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -699,7 +686,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -762,7 +749,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -814,7 +800,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + + /// Transforms this `Read` instance to an [`Iterator`] over its bytes. +@@ -851,7 +836,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes where Self: Sized { + Bytes { inner: self } + } +@@ -886,7 +870,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain where Self: Sized { + Chain { first: self, second: next, done_first: false } + } +@@ -922,22 +905,64 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take where Self: Sized { + Take { inner: self, limit: limit } + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -950,10 +975,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -989,7 +1013,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1013,7 +1036,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1023,7 +1045,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1036,11 +1057,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1053,10 +1072,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1091,7 +1109,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(mem::replace(&mut bufs, &mut []), 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1115,7 +1132,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1126,13 +1142,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1146,21 +1160,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1214,7 +1225,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1263,7 +1273,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1274,7 +1283,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1302,7 +1310,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1335,7 +1342,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1387,7 +1393,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1443,7 +1448,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + } + +@@ -1473,7 +1477,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1489,7 +1492,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1527,7 +1529,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1566,7 +1567,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1578,29 +1578,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + -> Result { + let mut read = 0; +@@ -1680,7 +1677,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1721,7 +1718,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1743,7 +1739,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1799,7 +1794,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1858,7 +1852,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1899,7 +1892,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split where Self: Sized { + Split { buf: self, delim: byte } + } +@@ -1938,7 +1930,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines where Self: Sized { + Lines { buf: self } + } +@@ -1950,7 +1941,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -1976,7 +1966,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -1999,7 +1988,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2026,13 +2014,11 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain") +@@ -2042,7 +2028,6 @@ impl fmt::Debug for Chain { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2074,7 +2059,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2101,7 +2086,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2136,7 +2120,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { self.limit } + + /// Sets the number of bytes that can be read before this instance will +@@ -2162,7 +2145,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2187,7 +2169,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2212,7 +2193,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2241,13 +2221,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2265,6 +2243,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2273,7 +2252,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2300,13 +2279,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2330,14 +2307,14 @@ impl Iterator for Bytes { + /// `BufRead`. Please see the documentation of `split()` for more details. + /// + /// [split]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2362,13 +2339,13 @@ impl Iterator for Split { + /// `BufRead`. Please see the documentation of `lines()` for more details. + /// + /// [lines]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 2e19edf..66294a3 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Write, Seek}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{Read, Write, BufRead, Seek}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index 33cc87e..75b8032 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, Read, Initializer, Write, ErrorKind, BufRead, IoSlice, IoSliceMut}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, Read, Initializer, Write, ErrorKind, IoSlice, IoSliceMut}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where R: Read, W: Write + { +@@ -70,7 +70,6 @@ pub fn copy(reader: &mut R, writer: &mut W) -> io::Result< + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { _priv: () } + + /// Constructs a new handle to an empty reader. +@@ -90,10 +89,8 @@ pub struct Empty { _priv: () } + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { Empty { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { Ok(0) } +@@ -103,7 +100,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(&[]) } +@@ -111,7 +109,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -124,7 +121,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { byte: u8 } + + /// Creates an instance of a reader that infinitely repeats one byte. +@@ -141,10 +137,8 @@ pub struct Repeat { byte: u8 } + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { Repeat { byte } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -169,7 +163,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -182,7 +175,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { _priv: () } + + /// Creates an instance of a writer which will successfully consume all data. +@@ -199,10 +191,8 @@ pub struct Sink { _priv: () } + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { Sink { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { Ok(buf.len()) } +@@ -217,7 +207,6 @@ impl Write for Sink { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/ab8995bbca73be761402585ead491111163c44d6.patch b/patches/ab8995bbca73be761402585ead491111163c44d6.patch new file mode 100644 index 0000000..faffea7 --- /dev/null +++ b/patches/ab8995bbca73be761402585ead491111163c44d6.patch @@ -0,0 +1,2084 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 02b0fc0..fe6e4af 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,8 +1,9 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, SizeHint, DEFAULT_BUF_SIZE, + }; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -44,7 +45,6 @@ use crate::io::{ + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -68,7 +68,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -89,7 +88,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buf = Box::new_uninit_slice(capacity).assume_init(); +@@ -118,7 +116,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -141,7 +138,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -169,7 +165,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -192,7 +187,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -216,7 +210,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -234,7 +227,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -254,7 +246,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -310,7 +301,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -330,7 +320,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -343,7 +332,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index 65bc2fc..46cd6b8 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,9 +1,9 @@ +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; +-use crate::mem; ++use core::mem; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -65,7 +65,6 @@ use crate::mem; + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -87,7 +86,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -105,7 +103,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -200,7 +197,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -220,7 +216,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -238,7 +233,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -270,7 +264,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -294,7 +287,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -325,7 +317,6 @@ impl BufWriter { + /// assert_eq!(recovered_writer.len(), 0); + /// assert_eq!(&buffered_data.unwrap(), b"ata"); + /// ``` +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_raw_parts(mut self) -> (W, Result, WriterPanicked>) { + let buf = mem::take(&mut self.buf); + let buf = if !self.panicked { Ok(buf) } else { Err(WriterPanicked { buf }) }; +@@ -333,7 +324,6 @@ impl BufWriter { + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + /// Error returned for the buffered data from `BufWriter::into_raw_parts`, when the underlying + /// writer has previously panicked. Contains the (possibly partly written) buffered data. + /// +@@ -367,7 +357,6 @@ pub struct WriterPanicked { + impl WriterPanicked { + /// Returns the perhaps-unwritten data. Some of this data may have been written by the + /// panicking call(s) to the underlying writer, so simply writing it again is not a good idea. +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_inner(self) -> Vec { + self.buf + } +@@ -376,22 +365,12 @@ impl WriterPanicked { + "BufWriter inner writer panicked, what data remains unwritten is not known"; + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] +-impl error::Error for WriterPanicked { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- Self::DESCRIPTION +- } +-} +- +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Display for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + write!(f, "{}", Self::DESCRIPTION) + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Debug for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("WriterPanicked") +@@ -400,7 +379,6 @@ impl fmt::Debug for WriterPanicked { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -497,7 +475,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -510,7 +487,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -521,7 +497,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index d0c859d..a052adf 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index 6549781..0dc7440 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,7 +119,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } +@@ -143,7 +139,6 @@ impl IntoInnerError { + /// let err = into_inner_err.into_error(); + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_error(self) -> Error { + self.1 + } +@@ -167,28 +162,17 @@ impl IntoInnerError { + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// assert_eq!(recovered_writer.buffer(), b"t be actually written"); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_parts(self) -> (Error, W) { + (self.1, self.0) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/copy.rs b/copy.rs +index eb60df2..df99a47 100644 +--- a/copy.rs ++++ b/copy.rs +@@ -1,5 +1,6 @@ +-use super::{BufWriter, ErrorKind, Read, Result, Write, DEFAULT_BUF_SIZE}; +-use crate::mem::MaybeUninit; ++use super::{ErrorKind, Read, Result, Write, DEFAULT_BUF_SIZE}; ++#[cfg(feature = "collections")] use super::BufWriter; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,19 +40,12 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> Result + where + R: Read, + W: Write, + { +- cfg_if::cfg_if! { +- if #[cfg(any(target_os = "linux", target_os = "android"))] { +- crate::sys::kernel_copy::copy_spec(reader, writer) +- } else { +- generic_copy(reader, writer) +- } +- } ++ generic_copy(reader, writer) + } + + /// The userspace read-write-loop implementation of `io::copy` that is used when +@@ -76,6 +70,7 @@ impl BufferedCopySpec for W { + } + } + ++#[cfg(feature = "collections")] + impl BufferedCopySpec for BufWriter { + fn copy_to(reader: &mut R, writer: &mut Self) -> Result { + if writer.capacity() < DEFAULT_BUF_SIZE { +diff --git a/cursor.rs b/cursor.rs +index bbee2cc..dc75216 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,8 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,8 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn get_ref(&self) -> &T { + &self.inner + } +@@ -152,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -176,8 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn position(&self) -> u64 { + self.pos + } +@@ -199,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -245,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -274,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -285,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -326,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -354,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -366,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -389,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -410,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -431,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 9870cfc..df98b8e 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,18 +1,22 @@ + #[cfg(test)] + mod tests; + +-use crate::alloc::Allocator; +-use crate::cmp; +-use crate::fmt; ++#[cfg(feature="collections")] use core::alloc::Allocator; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -34,11 +38,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -49,7 +55,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -81,14 +86,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -111,7 +115,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -133,11 +137,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -148,7 +154,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -180,14 +186,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -217,7 +223,6 @@ impl BufRead for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -280,6 +285,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -289,7 +295,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -311,7 +317,6 @@ impl BufRead for &[u8] { + /// If the number of bytes to be written exceeds the size of the slice, write operations will + /// return short writes: ultimately, `Ok(0)`; in this situation, `write_all` returns an error of + /// kind `ErrorKind::WriteZero`. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -357,7 +362,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 17002e3..dde604d 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -246,58 +246,48 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::copy::copy; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[unstable(feature = "internal_output_capture", issue = "none")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::set_output_capture; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + pub(crate) mod copy; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -324,6 +314,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -351,10 +342,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -504,7 +497,6 @@ pub(crate) fn default_read_exact(this: &mut R, mut buf: &mut [ + /// [`&str`]: prim@str + /// [`std::io`]: self + /// [`File`]: crate::fs::File +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -575,7 +567,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -587,7 +578,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -600,7 +590,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -624,7 +613,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -676,7 +664,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -719,7 +707,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -783,7 +771,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, buf: &mut [u8]) -> Result<()> { + default_read_exact(self, buf) + } +@@ -822,7 +809,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -859,7 +845,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -897,7 +882,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -936,7 +920,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -986,29 +969,71 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +-#[unstable(feature = "io_read_to_string", issue = "80218")] ++#[cfg(feature="collections")] + pub fn read_to_string(reader: &mut R) -> Result { + let mut buf = String::new(); + reader.read_to_string(&mut buf)?; + Ok(buf) + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1021,10 +1046,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1059,7 +1083,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1083,7 +1106,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1093,7 +1115,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1106,18 +1127,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1130,10 +1147,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1167,7 +1183,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1191,7 +1206,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1202,13 +1216,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1222,21 +1234,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1290,7 +1299,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1337,7 +1345,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1350,7 +1357,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1365,7 +1371,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1393,7 +1398,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1427,7 +1431,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1489,7 +1492,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1542,7 +1544,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1598,7 +1599,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1633,7 +1633,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1647,7 +1646,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1684,7 +1682,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_stream_len", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1721,7 +1718,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "seek_convenience", since = "1.51.0")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1731,29 +1727,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1829,7 +1822,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1870,7 +1863,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1892,7 +1884,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1949,7 +1940,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -2012,7 +2002,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2050,7 +2039,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2087,7 +2075,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2102,7 +2089,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2128,7 +2114,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2151,7 +2136,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2178,20 +2162,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2219,7 +2200,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2257,7 +2238,6 @@ impl SizeHint for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2290,7 +2270,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2318,7 +2297,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2343,7 +2321,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2368,7 +2345,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2397,13 +2373,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2421,6 +2395,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2429,7 +2404,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2456,13 +2431,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2510,14 +2483,14 @@ impl SizeHint for T { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2542,13 +2515,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index d806431..6b9791a 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index f472361..0a1899d 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,16 +3,16 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; ++use core::fmt; + use crate::io::{ +- self, BufRead, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, SizeHint, Write, ++ self, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, SizeHint, Write, + }; ++#[cfg(feature="collections")] use crate::io::BufRead; + + /// A reader which is always at EOF. + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -32,13 +32,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -50,7 +47,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -60,7 +58,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "empty_seek", since = "1.51.0")] + impl Seek for Empty { + fn seek(&mut self, _pos: SeekFrom) -> io::Result { + Ok(0) +@@ -75,7 +72,6 @@ impl Seek for Empty { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -92,7 +88,6 @@ impl SizeHint for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -111,13 +106,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -147,7 +139,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -158,7 +149,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -179,13 +169,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -209,7 +196,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -233,7 +219,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/b03d3dc478ba13f405cf9a877a4894de096a1cc1.patch b/patches/b03d3dc478ba13f405cf9a877a4894de096a1cc1.patch new file mode 100644 index 0000000..cc43f5a --- /dev/null +++ b/patches/b03d3dc478ba13f405cf9a877a4894de096a1cc1.patch @@ -0,0 +1,1797 @@ +diff --git a/buffered.rs b/buffered.rs +index 9593a1b..0b6c3eb 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,13 +1,13 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, Initializer, DEFAULT_BUF_SIZE, Error, ErrorKind, SeekFrom, IoSlice, + IoSliceMut}; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -47,7 +47,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -71,7 +70,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -92,7 +90,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -127,7 +124,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { &self.inner } + + /// Gets a mutable reference to the underlying reader. +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { &mut self.inner } + + /// Returns a reference to the internally buffered data. +@@ -172,7 +167,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -195,7 +189,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { self.inner } + + /// Invalidates all data in the internal buffer. +@@ -211,7 +204,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -231,7 +223,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -269,7 +260,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -289,7 +279,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader where R: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufReader") +@@ -299,7 +288,6 @@ impl fmt::Debug for BufReader where R: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -410,7 +398,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -445,7 +432,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -460,7 +446,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -478,7 +463,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { + inner: Some(inner), +@@ -527,7 +511,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.as_ref().unwrap() } + + /// Gets a mutable reference to the underlying writer. +@@ -545,7 +528,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.as_mut().unwrap() } + + /// Returns a reference to the internally buffered data. +@@ -561,7 +543,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -585,7 +566,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -594,7 +574,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -630,7 +609,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufWriter") +@@ -640,7 +618,6 @@ impl fmt::Debug for BufWriter where W: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -650,7 +627,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -689,7 +665,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { &self.1 } + + /// Returns the buffered writer instance which generated the error. +@@ -722,23 +697,13 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { self.0 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { iie.1 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -809,7 +774,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -830,7 +794,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -851,7 +814,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { + inner: BufWriter::with_capacity(capacity, inner), +@@ -875,7 +837,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.get_ref() } + + /// Gets a mutable reference to the underlying writer. +@@ -898,7 +859,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.get_mut() } + + /// Unwraps this `LineWriter`, returning the underlying writer. +@@ -924,7 +884,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { +@@ -935,7 +894,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -980,7 +938,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("LineWriter") +diff --git a/cursor.rs b/cursor.rs +index a94176e..7768d39 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Initializer, SeekFrom, Error, ErrorKind, IoSlice, IoSliceMut}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { self.inner } + + /// Gets a reference to the underlying value in this cursor. +@@ -128,7 +125,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { &self.inner } + + /// Gets a mutable reference to the underlying value in this cursor. +@@ -147,7 +143,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { &mut self.inner } + + /// Returns the current position of this cursor. +@@ -169,7 +164,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { self.pos } + + /// Sets the position of this cursor. +@@ -189,11 +183,9 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { self.pos = pos; } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor where T: AsRef<[u8]> { + fn seek(&mut self, style: SeekFrom) -> io::Result { + let (base_pos, offset) = match style { +@@ -222,10 +214,9 @@ impl io::Seek for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor where T: AsRef<[u8]> { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -244,7 +235,7 @@ impl Read for Cursor where T: AsRef<[u8]> { + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -255,12 +246,16 @@ impl Read for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor where T: AsRef<[u8]> { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++impl Cursor where T: AsRef<[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor where T: AsRef<[u8]> { ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { self.get_buf() } + fn consume(&mut self, amt: usize) { self.pos += amt as u64; } + } + +@@ -292,6 +287,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new(ErrorKind::InvalidInput, +@@ -318,6 +314,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -331,7 +328,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -347,7 +343,7 @@ impl Write for Cursor<&mut [u8]> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -361,7 +357,7 @@ impl Write for Cursor<&mut Vec> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -375,8 +371,8 @@ impl Write for Cursor> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index c29a68e..c94d8c5 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,13 @@ +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; +-use crate::convert::From; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++use core::convert::Into; ++use core::fmt; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++use core::result; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; ++use core::convert::From; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +43,6 @@ use crate::convert::From; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +56,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +69,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +90,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +130,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +142,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +156,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +186,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -245,14 +230,13 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error +- where E: Into> ++ where E: Into + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { + repr: Repr::Custom(Box::new(Custom { + kind, +@@ -261,24 +245,6 @@ impl Error { + } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -304,7 +270,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -335,7 +300,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -369,12 +333,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error+Send+Sync+'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -440,12 +403,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error+Send+Sync+'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -474,8 +436,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -501,10 +462,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -516,22 +476,18 @@ impl fmt::Debug for Repr { + match *self { + Repr::Os(code) => + fmt.debug_struct("Os") +- .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)).finish(), ++ .field("code", &code).finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), + } + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -539,33 +495,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index c959f2d..b645bc8 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,13 +1,15 @@ +-use crate::cmp; +-use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, BufRead, Error, ErrorKind, +- IoSliceMut, IoSlice}; +-use crate::fmt; +-use crate::mem; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++use core::cmp; ++use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, Error, ErrorKind, IoSliceMut, IoSlice}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::fmt; ++use core::mem; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -24,11 +26,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -39,7 +43,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -62,12 +65,11 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -86,7 +88,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -103,11 +105,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -118,7 +122,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -141,12 +145,12 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -186,7 +190,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -245,6 +248,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -254,7 +258,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(*self) } +@@ -268,7 +272,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -307,7 +310,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 0386dbd..d7760e0 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,50 +257,38 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::slice; +-use crate::str; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(feature="collections")] use collections::string::String; ++use core::str; ++#[cfg(feature="collections")] use collections::vec::Vec; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::slice; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++ ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Result, Error, ErrorKind}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, sink, Sink, empty, Empty, repeat, Repeat}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stdin, stdout, stderr, Stdin, Stdout, Stderr}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StdoutLock, StderrLock, StdinLock}; +-#[unstable(feature = "print_internals", issue = "0")] +-pub use self::stdio::{_print, _eprint}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; + + pub mod prelude; +-mod buffered; ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + mod util; +-mod stdio; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { buf: &'a mut Vec, len: usize } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { self.buf.set_len(self.len); } +@@ -325,6 +313,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where F: FnOnce(&mut Vec) -> Result + { +@@ -352,10 +341,12 @@ fn append_to_string(buf: &mut String, f: F) -> Result + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -497,7 +488,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -565,7 +555,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -576,7 +565,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -603,7 +591,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -656,7 +643,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -699,7 +686,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -762,7 +749,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -814,7 +800,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + + /// Transforms this `Read` instance to an [`Iterator`] over its bytes. +@@ -851,7 +836,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes where Self: Sized { + Bytes { inner: self } + } +@@ -886,7 +870,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain where Self: Sized { + Chain { first: self, second: next, done_first: false } + } +@@ -922,22 +905,64 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take where Self: Sized { + Take { inner: self, limit: limit } + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -950,10 +975,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -989,7 +1013,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1013,7 +1036,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1023,7 +1045,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1036,11 +1057,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1053,10 +1072,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1091,7 +1109,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(mem::replace(&mut bufs, &mut []), 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1115,7 +1132,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1126,13 +1142,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1146,21 +1160,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1214,7 +1225,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1263,7 +1273,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1274,7 +1283,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1302,7 +1310,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1335,7 +1342,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1387,7 +1393,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1443,7 +1448,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + } + +@@ -1473,7 +1477,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1489,7 +1492,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1527,7 +1529,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1566,7 +1567,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1578,29 +1578,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + -> Result { + let mut read = 0; +@@ -1680,7 +1677,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1721,7 +1718,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1743,7 +1739,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1799,7 +1794,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1858,7 +1852,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1899,7 +1892,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split where Self: Sized { + Split { buf: self, delim: byte } + } +@@ -1938,7 +1930,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines where Self: Sized { + Lines { buf: self } + } +@@ -1950,7 +1941,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -1976,7 +1966,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -1999,7 +1988,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2026,13 +2014,11 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain") +@@ -2042,7 +2028,6 @@ impl fmt::Debug for Chain { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2074,7 +2059,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2101,7 +2086,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2136,7 +2120,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { self.limit } + + /// Sets the number of bytes that can be read before this instance will +@@ -2162,7 +2145,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2187,7 +2169,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2212,7 +2193,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2241,13 +2221,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2265,6 +2243,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2273,7 +2252,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2300,13 +2279,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2330,14 +2307,14 @@ impl Iterator for Bytes { + /// `BufRead`. Please see the documentation of `split()` for more details. + /// + /// [split]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2362,13 +2339,13 @@ impl Iterator for Split { + /// `BufRead`. Please see the documentation of `lines()` for more details. + /// + /// [lines]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 2e19edf..66294a3 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Write, Seek}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{Read, Write, BufRead, Seek}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index 33cc87e..75b8032 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, Read, Initializer, Write, ErrorKind, BufRead, IoSlice, IoSliceMut}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, Read, Initializer, Write, ErrorKind, IoSlice, IoSliceMut}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where R: Read, W: Write + { +@@ -70,7 +70,6 @@ pub fn copy(reader: &mut R, writer: &mut W) -> io::Result< + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { _priv: () } + + /// Constructs a new handle to an empty reader. +@@ -90,10 +89,8 @@ pub struct Empty { _priv: () } + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { Empty { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { Ok(0) } +@@ -103,7 +100,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(&[]) } +@@ -111,7 +109,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -124,7 +121,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { byte: u8 } + + /// Creates an instance of a reader that infinitely repeats one byte. +@@ -141,10 +137,8 @@ pub struct Repeat { byte: u8 } + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { Repeat { byte } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -169,7 +163,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -182,7 +175,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { _priv: () } + + /// Creates an instance of a writer which will successfully consume all data. +@@ -199,10 +191,8 @@ pub struct Sink { _priv: () } + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { Sink { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { Ok(buf.len()) } +@@ -217,7 +207,6 @@ impl Write for Sink { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/b3e0d272af149c4126f90a0262d796d7401ba7a1.patch b/patches/b3e0d272af149c4126f90a0262d796d7401ba7a1.patch new file mode 100644 index 0000000..8b69c4b --- /dev/null +++ b/patches/b3e0d272af149c4126f90a0262d796d7401ba7a1.patch @@ -0,0 +1,1848 @@ +diff --git a/buffered.rs b/buffered.rs +index 8862226..7898006 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -222,7 +215,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -240,7 +232,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -260,7 +251,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -298,7 +288,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -318,7 +307,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -331,7 +319,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -442,7 +429,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -477,7 +463,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -492,7 +477,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -510,7 +494,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -557,7 +540,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -577,7 +559,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -595,7 +576,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -616,7 +596,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -640,7 +619,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -649,7 +627,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -685,7 +662,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -698,7 +674,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -708,7 +683,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -747,7 +721,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -782,28 +755,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -874,7 +836,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -895,7 +856,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -916,7 +876,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -937,7 +896,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -962,7 +920,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -990,7 +947,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -998,7 +954,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1104,7 +1059,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index 9787cbb..1cf83d3 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -268,7 +259,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -279,15 +270,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -320,6 +320,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -348,6 +349,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -360,7 +362,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -378,7 +379,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -394,7 +395,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -410,8 +411,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index 3b55d9b..c754d1f 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -432,12 +396,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -466,8 +429,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -493,10 +455,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -509,8 +470,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -518,13 +477,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -532,34 +489,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index b7f82e6..c857f83 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -25,11 +29,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -40,7 +46,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -67,14 +72,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -97,7 +101,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -114,11 +118,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -129,7 +135,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -156,14 +162,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -207,7 +213,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -265,6 +270,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -274,7 +280,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -292,7 +298,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -333,7 +338,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 67b382c..f8ccb5e 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,53 +257,43 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -330,6 +320,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -357,10 +348,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -496,7 +489,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -564,7 +556,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -575,7 +566,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -602,7 +592,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -655,7 +644,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -698,7 +687,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -761,7 +750,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -815,7 +803,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -857,7 +844,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -895,7 +881,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -934,7 +919,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -943,16 +927,59 @@ pub trait Read { + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -965,10 +992,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1003,7 +1029,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1027,7 +1052,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1037,7 +1061,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1050,11 +1073,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1067,10 +1088,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1104,7 +1124,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1128,7 +1147,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1139,13 +1157,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1159,21 +1175,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1227,7 +1240,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1276,7 +1288,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1287,7 +1298,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1315,7 +1325,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1350,7 +1359,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1403,7 +1411,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1459,7 +1466,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1494,7 +1500,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1510,7 +1515,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1548,7 +1552,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1587,7 +1590,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1599,29 +1601,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1700,7 +1699,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1741,7 +1740,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1763,7 +1761,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1819,7 +1816,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1878,7 +1874,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1919,7 +1914,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -1961,7 +1955,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -1976,7 +1969,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2002,7 +1994,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2025,7 +2016,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2052,20 +2042,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2093,7 +2080,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2118,7 +2105,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2153,7 +2139,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2181,7 +2166,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2206,7 +2190,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2231,7 +2214,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2260,13 +2242,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2284,6 +2264,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2292,7 +2273,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2319,13 +2300,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2349,14 +2328,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2381,13 +2360,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b09161b..e52119e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -185,7 +179,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -217,12 +209,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -241,7 +231,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/b405aa2d0301c5fc448299501278ae2db4e15e50.patch b/patches/b405aa2d0301c5fc448299501278ae2db4e15e50.patch new file mode 100644 index 0000000..23b5094 --- /dev/null +++ b/patches/b405aa2d0301c5fc448299501278ae2db4e15e50.patch @@ -0,0 +1,1761 @@ +diff --git a/buffered.rs b/buffered.rs +index aaf628e..259eba3 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,13 +1,13 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, Initializer, DEFAULT_BUF_SIZE, Error, ErrorKind, SeekFrom, IoSlice, + IoSliceMut}; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -47,7 +47,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -71,7 +70,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -92,7 +90,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -127,7 +124,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { &self.inner } + + /// Gets a mutable reference to the underlying reader. +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { &mut self.inner } + + /// Returns a reference to the internally buffered data. +@@ -172,7 +167,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -195,7 +189,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { self.inner } + + /// Invalidates all data in the internal buffer. +@@ -211,7 +204,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -231,7 +223,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -269,7 +260,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -289,7 +279,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader where R: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufReader") +@@ -299,7 +288,6 @@ impl fmt::Debug for BufReader where R: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -408,7 +396,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -443,7 +430,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -458,7 +444,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -476,7 +461,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { + inner: Some(inner), +@@ -525,7 +509,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.as_ref().unwrap() } + + /// Gets a mutable reference to the underlying writer. +@@ -543,7 +526,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.as_mut().unwrap() } + + /// Returns a reference to the internally buffered data. +@@ -559,7 +541,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -583,7 +564,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -592,7 +572,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -628,7 +607,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufWriter") +@@ -638,7 +616,6 @@ impl fmt::Debug for BufWriter where W: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -648,7 +625,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -687,7 +663,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { &self.1 } + + /// Returns the buffered writer instance which generated the error. +@@ -720,23 +695,13 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { self.0 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { iie.1 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -807,7 +772,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -828,7 +792,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -849,7 +812,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { + inner: BufWriter::with_capacity(capacity, inner), +@@ -873,7 +835,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.get_ref() } + + /// Gets a mutable reference to the underlying writer. +@@ -896,7 +857,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.get_mut() } + + /// Unwraps this `LineWriter`, returning the underlying writer. +@@ -922,7 +882,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { +@@ -933,7 +892,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -978,7 +936,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("LineWriter") +diff --git a/cursor.rs b/cursor.rs +index a94176e..7768d39 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Initializer, SeekFrom, Error, ErrorKind, IoSlice, IoSliceMut}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { self.inner } + + /// Gets a reference to the underlying value in this cursor. +@@ -128,7 +125,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { &self.inner } + + /// Gets a mutable reference to the underlying value in this cursor. +@@ -147,7 +143,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { &mut self.inner } + + /// Returns the current position of this cursor. +@@ -169,7 +164,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { self.pos } + + /// Sets the position of this cursor. +@@ -189,11 +183,9 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { self.pos = pos; } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor where T: AsRef<[u8]> { + fn seek(&mut self, style: SeekFrom) -> io::Result { + let (base_pos, offset) = match style { +@@ -222,10 +214,9 @@ impl io::Seek for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor where T: AsRef<[u8]> { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -244,7 +235,7 @@ impl Read for Cursor where T: AsRef<[u8]> { + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -255,12 +246,16 @@ impl Read for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor where T: AsRef<[u8]> { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++impl Cursor where T: AsRef<[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor where T: AsRef<[u8]> { ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { self.get_buf() } + fn consume(&mut self, amt: usize) { self.pos += amt as u64; } + } + +@@ -292,6 +287,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new(ErrorKind::InvalidInput, +@@ -318,6 +314,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -331,7 +328,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -347,7 +343,7 @@ impl Write for Cursor<&mut [u8]> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -361,7 +357,7 @@ impl Write for Cursor<&mut Vec> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -375,8 +371,8 @@ impl Write for Cursor> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index c29a68e..c94d8c5 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,13 @@ +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; +-use crate::convert::From; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++use core::convert::Into; ++use core::fmt; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++use core::result; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; ++use core::convert::From; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +43,6 @@ use crate::convert::From; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +56,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +69,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +90,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +130,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +142,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +156,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +186,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -245,14 +230,13 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error +- where E: Into> ++ where E: Into + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { + repr: Repr::Custom(Box::new(Custom { + kind, +@@ -261,24 +245,6 @@ impl Error { + } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -304,7 +270,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -335,7 +300,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -369,12 +333,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error+Send+Sync+'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -440,12 +403,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error+Send+Sync+'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -474,8 +436,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -501,10 +462,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -516,22 +476,18 @@ impl fmt::Debug for Repr { + match *self { + Repr::Os(code) => + fmt.debug_struct("Os") +- .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)).finish(), ++ .field("code", &code).finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), + } + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -539,33 +495,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index c959f2d..b645bc8 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,13 +1,15 @@ +-use crate::cmp; +-use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, BufRead, Error, ErrorKind, +- IoSliceMut, IoSlice}; +-use crate::fmt; +-use crate::mem; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++use core::cmp; ++use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, Error, ErrorKind, IoSliceMut, IoSlice}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::fmt; ++use core::mem; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -24,11 +26,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -39,7 +43,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -62,12 +65,11 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -86,7 +88,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -103,11 +105,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -118,7 +122,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -141,12 +145,12 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -186,7 +190,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -245,6 +248,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -254,7 +258,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(*self) } +@@ -268,7 +272,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -307,7 +310,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 09b6b69..fdcc2de 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,50 +257,38 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::slice; +-use crate::str; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(feature="collections")] use collections::string::String; ++use core::str; ++#[cfg(feature="collections")] use collections::vec::Vec; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::slice; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++ ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Result, Error, ErrorKind}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, sink, Sink, empty, Empty, repeat, Repeat}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stdin, stdout, stderr, Stdin, Stdout, Stderr}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StdoutLock, StderrLock, StdinLock}; +-#[unstable(feature = "print_internals", issue = "0")] +-pub use self::stdio::{_print, _eprint}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; + + pub mod prelude; +-mod buffered; ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + mod util; +-mod stdio; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { buf: &'a mut Vec, len: usize } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { self.buf.set_len(self.len); } +@@ -325,6 +313,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where F: FnOnce(&mut Vec) -> Result + { +@@ -352,10 +341,12 @@ fn append_to_string(buf: &mut String, f: F) -> Result + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation(r: &mut R, + buf: &mut Vec, + reservation_size: usize) -> Result +@@ -484,7 +475,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -552,7 +542,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -563,7 +552,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -590,7 +578,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -643,7 +630,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -686,7 +673,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -749,7 +736,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -801,7 +787,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + + /// Transforms this `Read` instance to an [`Iterator`] over its bytes. +@@ -838,7 +823,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes where Self: Sized { + Bytes { inner: self } + } +@@ -873,7 +857,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain where Self: Sized { + Chain { first: self, second: next, done_first: false } + } +@@ -909,22 +892,52 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take where Self: Sized { + Take { inner: self, limit: limit } + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -937,14 +950,12 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -954,7 +965,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -967,11 +977,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -984,14 +992,12 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1002,13 +1008,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1022,21 +1026,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1090,7 +1091,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1139,7 +1139,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1150,7 +1149,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1178,7 +1176,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1211,7 +1208,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1263,7 +1259,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1319,7 +1314,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + } + +@@ -1349,7 +1343,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1365,7 +1358,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1403,7 +1395,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1442,7 +1433,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1454,29 +1444,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + -> Result { + let mut read = 0; +@@ -1556,7 +1543,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1597,7 +1584,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1619,7 +1605,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1675,7 +1660,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1734,7 +1718,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1775,7 +1758,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split where Self: Sized { + Split { buf: self, delim: byte } + } +@@ -1814,7 +1796,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines where Self: Sized { + Lines { buf: self } + } +@@ -1826,7 +1807,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -1852,7 +1832,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -1875,7 +1854,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -1902,13 +1880,11 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain") +@@ -1918,7 +1894,6 @@ impl fmt::Debug for Chain { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -1950,7 +1925,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -1977,7 +1952,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2012,7 +1986,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { self.limit } + + /// Sets the number of bytes that can be read before this instance will +@@ -2038,7 +2011,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2063,7 +2035,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2088,7 +2059,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2117,13 +2087,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2141,6 +2109,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + let reservation_size = cmp::min(self.limit, 32) as usize; + +@@ -2148,7 +2117,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2175,13 +2144,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2205,14 +2172,14 @@ impl Iterator for Bytes { + /// `BufRead`. Please see the documentation of `split()` for more details. + /// + /// [split]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2237,13 +2204,13 @@ impl Iterator for Split { + /// `BufRead`. Please see the documentation of `lines()` for more details. + /// + /// [lines]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 2e19edf..66294a3 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Write, Seek}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{Read, Write, BufRead, Seek}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index 33cc87e..75b8032 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, Read, Initializer, Write, ErrorKind, BufRead, IoSlice, IoSliceMut}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, Read, Initializer, Write, ErrorKind, IoSlice, IoSliceMut}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where R: Read, W: Write + { +@@ -70,7 +70,6 @@ pub fn copy(reader: &mut R, writer: &mut W) -> io::Result< + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { _priv: () } + + /// Constructs a new handle to an empty reader. +@@ -90,10 +89,8 @@ pub struct Empty { _priv: () } + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { Empty { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { Ok(0) } +@@ -103,7 +100,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(&[]) } +@@ -111,7 +109,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -124,7 +121,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { byte: u8 } + + /// Creates an instance of a reader that infinitely repeats one byte. +@@ -141,10 +137,8 @@ pub struct Repeat { byte: u8 } + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { Repeat { byte } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -169,7 +163,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -182,7 +175,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { _priv: () } + + /// Creates an instance of a writer which will successfully consume all data. +@@ -199,10 +191,8 @@ pub struct Sink { _priv: () } + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { Sink { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { Ok(buf.len()) } +@@ -217,7 +207,6 @@ impl Write for Sink { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/b777552167d2651ceb13437f9fde4dca95045912.patch b/patches/b777552167d2651ceb13437f9fde4dca95045912.patch new file mode 100644 index 0000000..49eae3a --- /dev/null +++ b/patches/b777552167d2651ceb13437f9fde4dca95045912.patch @@ -0,0 +1,2002 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 16c18d6..f392e3c 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,6 +1,7 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DEFAULT_BUF_SIZE}; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -42,7 +43,6 @@ use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DE + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -66,7 +66,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -87,7 +86,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -117,7 +115,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -140,7 +137,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -168,7 +164,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -191,7 +186,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -215,7 +209,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -233,7 +226,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -253,7 +245,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -295,7 +286,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -315,7 +305,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -328,7 +317,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index 067ed6b..47869a7 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,7 +1,8 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -63,7 +64,6 @@ use crate::io::{ + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -85,7 +85,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -103,7 +102,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -198,7 +196,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -218,7 +215,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -236,7 +232,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -256,7 +251,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -280,7 +274,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -289,7 +282,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -353,7 +345,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -366,7 +357,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -377,7 +367,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index a80d08d..20bd401 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index 6549781..0dc7440 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,7 +119,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } +@@ -143,7 +139,6 @@ impl IntoInnerError { + /// let err = into_inner_err.into_error(); + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_error(self) -> Error { + self.1 + } +@@ -167,28 +162,17 @@ impl IntoInnerError { + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// assert_eq!(recovered_writer.buffer(), b"t be actually written"); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_parts(self) -> (Error, W) { + (self.1, self.0) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/copy.rs b/copy.rs +index b88bca2..7593702 100644 +--- a/copy.rs ++++ b/copy.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, ErrorKind, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,19 +39,12 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, + W: Write, + { +- cfg_if::cfg_if! { +- if #[cfg(any(target_os = "linux", target_os = "android"))] { +- crate::sys::kernel_copy::copy_spec(reader, writer) +- } else { +- generic_copy(reader, writer) +- } +- } ++ generic_copy(reader, writer) + } + + /// The general read-write-loop implementation of +diff --git a/cursor.rs b/cursor.rs +index bbee2cc..dc75216 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,8 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,8 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn get_ref(&self) -> &T { + &self.inner + } +@@ -152,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -176,8 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn position(&self) -> u64 { + self.pos + } +@@ -199,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -245,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -274,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -285,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -326,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -354,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -366,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -389,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -410,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -431,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 00bf8b9..5c0e7cd 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -216,7 +222,6 @@ impl BufRead for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -279,6 +284,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -288,7 +294,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -310,7 +316,6 @@ impl BufRead for &[u8] { + /// If the number of bytes to be written exceeds the size of the slice, write operations will + /// return short writes: ultimately, `Ok(0)`; in this situation, `write_all` returns an error of + /// kind `ErrorKind::WriteZero`. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -356,7 +361,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index dfbf6c3..7437b18 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -247,58 +247,48 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::copy::copy; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[unstable(feature = "internal_output_capture", issue = "none")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::set_output_capture; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + pub(crate) mod copy; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -325,6 +315,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -352,10 +343,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -489,7 +482,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -560,7 +552,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -572,7 +563,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -585,7 +575,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -609,7 +598,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -661,7 +649,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -704,7 +692,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -768,7 +756,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -822,7 +809,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -859,7 +845,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -897,7 +882,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -936,7 +920,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -945,22 +928,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -973,10 +998,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1011,7 +1035,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1035,7 +1058,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1045,7 +1067,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1058,18 +1079,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1082,10 +1099,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1119,7 +1135,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1143,7 +1158,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1154,13 +1168,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1174,21 +1186,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1242,7 +1251,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1289,7 +1297,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1302,7 +1309,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1317,7 +1323,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1345,7 +1350,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1379,7 +1383,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1441,7 +1444,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1494,7 +1496,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1550,7 +1551,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1585,7 +1585,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1599,7 +1598,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1636,7 +1634,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1674,7 +1671,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1684,29 +1680,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1782,7 +1775,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1823,7 +1816,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1845,7 +1837,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1902,7 +1893,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1965,7 +1955,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2004,7 +1993,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2041,7 +2029,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2056,7 +2043,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2082,7 +2068,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2105,7 +2090,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2132,20 +2116,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2173,7 +2154,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2198,7 +2179,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2231,7 +2211,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2259,7 +2238,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2284,7 +2262,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2309,7 +2286,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2338,13 +2314,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2362,6 +2336,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2370,7 +2345,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2397,13 +2372,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2427,14 +2400,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2459,13 +2432,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index db84545..8e88c3d 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,14 +3,14 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, Initializer, IoSlice, IoSliceMut, Read, Write}; ++use core::fmt; ++use crate::io::{self, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; + + /// A reader which is always at EOF. + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -30,13 +30,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -48,7 +45,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -58,7 +56,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -69,7 +66,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -88,13 +84,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -124,7 +117,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -135,7 +127,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -156,13 +147,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -186,7 +174,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -210,7 +197,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/b94e59cc41f8eeb36ee269cae3275d7620189c14.patch b/patches/b94e59cc41f8eeb36ee269cae3275d7620189c14.patch new file mode 100644 index 0000000..864085b --- /dev/null +++ b/patches/b94e59cc41f8eeb36ee269cae3275d7620189c14.patch @@ -0,0 +1,1761 @@ +diff --git a/buffered.rs b/buffered.rs +index aaf628e..259eba3 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,13 +1,13 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, Initializer, DEFAULT_BUF_SIZE, Error, ErrorKind, SeekFrom, IoSlice, + IoSliceMut}; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -47,7 +47,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -71,7 +70,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -92,7 +90,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -127,7 +124,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { &self.inner } + + /// Gets a mutable reference to the underlying reader. +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { &mut self.inner } + + /// Returns a reference to the internally buffered data. +@@ -172,7 +167,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -195,7 +189,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { self.inner } + + /// Invalidates all data in the internal buffer. +@@ -211,7 +204,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -231,7 +223,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -269,7 +260,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -289,7 +279,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader where R: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufReader") +@@ -299,7 +288,6 @@ impl fmt::Debug for BufReader where R: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -408,7 +396,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -443,7 +430,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -458,7 +444,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -476,7 +461,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { + inner: Some(inner), +@@ -525,7 +509,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.as_ref().unwrap() } + + /// Gets a mutable reference to the underlying writer. +@@ -543,7 +526,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.as_mut().unwrap() } + + /// Returns a reference to the internally buffered data. +@@ -559,7 +541,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -583,7 +564,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -592,7 +572,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -628,7 +607,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufWriter") +@@ -638,7 +616,6 @@ impl fmt::Debug for BufWriter where W: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -648,7 +625,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -687,7 +663,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { &self.1 } + + /// Returns the buffered writer instance which generated the error. +@@ -720,23 +695,13 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { self.0 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { iie.1 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -807,7 +772,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -828,7 +792,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -849,7 +812,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { + inner: BufWriter::with_capacity(capacity, inner), +@@ -873,7 +835,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.get_ref() } + + /// Gets a mutable reference to the underlying writer. +@@ -896,7 +857,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.get_mut() } + + /// Unwraps this `LineWriter`, returning the underlying writer. +@@ -922,7 +882,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { +@@ -933,7 +892,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -978,7 +936,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("LineWriter") +diff --git a/cursor.rs b/cursor.rs +index a94176e..7768d39 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Initializer, SeekFrom, Error, ErrorKind, IoSlice, IoSliceMut}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { self.inner } + + /// Gets a reference to the underlying value in this cursor. +@@ -128,7 +125,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { &self.inner } + + /// Gets a mutable reference to the underlying value in this cursor. +@@ -147,7 +143,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { &mut self.inner } + + /// Returns the current position of this cursor. +@@ -169,7 +164,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { self.pos } + + /// Sets the position of this cursor. +@@ -189,11 +183,9 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { self.pos = pos; } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor where T: AsRef<[u8]> { + fn seek(&mut self, style: SeekFrom) -> io::Result { + let (base_pos, offset) = match style { +@@ -222,10 +214,9 @@ impl io::Seek for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor where T: AsRef<[u8]> { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -244,7 +235,7 @@ impl Read for Cursor where T: AsRef<[u8]> { + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -255,12 +246,16 @@ impl Read for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor where T: AsRef<[u8]> { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++impl Cursor where T: AsRef<[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor where T: AsRef<[u8]> { ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { self.get_buf() } + fn consume(&mut self, amt: usize) { self.pos += amt as u64; } + } + +@@ -292,6 +287,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new(ErrorKind::InvalidInput, +@@ -318,6 +314,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -331,7 +328,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -347,7 +343,7 @@ impl Write for Cursor<&mut [u8]> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -361,7 +357,7 @@ impl Write for Cursor<&mut Vec> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -375,8 +371,8 @@ impl Write for Cursor> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index c29a68e..c94d8c5 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,13 @@ +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; +-use crate::convert::From; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++use core::convert::Into; ++use core::fmt; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++use core::result; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; ++use core::convert::From; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +43,6 @@ use crate::convert::From; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +56,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +69,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +90,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +130,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +142,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +156,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +186,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -245,14 +230,13 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error +- where E: Into> ++ where E: Into + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { + repr: Repr::Custom(Box::new(Custom { + kind, +@@ -261,24 +245,6 @@ impl Error { + } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -304,7 +270,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -335,7 +300,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -369,12 +333,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error+Send+Sync+'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -440,12 +403,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error+Send+Sync+'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -474,8 +436,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -501,10 +462,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -516,22 +476,18 @@ impl fmt::Debug for Repr { + match *self { + Repr::Os(code) => + fmt.debug_struct("Os") +- .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)).finish(), ++ .field("code", &code).finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), + } + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -539,33 +495,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index c959f2d..b645bc8 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,13 +1,15 @@ +-use crate::cmp; +-use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, BufRead, Error, ErrorKind, +- IoSliceMut, IoSlice}; +-use crate::fmt; +-use crate::mem; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++use core::cmp; ++use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, Error, ErrorKind, IoSliceMut, IoSlice}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::fmt; ++use core::mem; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -24,11 +26,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -39,7 +43,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -62,12 +65,11 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -86,7 +88,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -103,11 +105,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -118,7 +122,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -141,12 +145,12 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -186,7 +190,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -245,6 +248,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -254,7 +258,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(*self) } +@@ -268,7 +272,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -307,7 +310,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index e951b57..919f4ec 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,50 +257,38 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::slice; +-use crate::str; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(feature="collections")] use collections::string::String; ++use core::str; ++#[cfg(feature="collections")] use collections::vec::Vec; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::slice; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++ ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Result, Error, ErrorKind}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, sink, Sink, empty, Empty, repeat, Repeat}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stdin, stdout, stderr, Stdin, Stdout, Stderr}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StdoutLock, StderrLock, StdinLock}; +-#[unstable(feature = "print_internals", issue = "0")] +-pub use self::stdio::{_print, _eprint}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; + + pub mod prelude; +-mod buffered; ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + mod util; +-mod stdio; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { buf: &'a mut Vec, len: usize } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { self.buf.set_len(self.len); } +@@ -325,6 +313,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where F: FnOnce(&mut Vec) -> Result + { +@@ -352,10 +341,12 @@ fn append_to_string(buf: &mut String, f: F) -> Result + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation(r: &mut R, + buf: &mut Vec, + reservation_size: usize) -> Result +@@ -484,7 +475,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -552,7 +542,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -563,7 +552,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -590,7 +578,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -643,7 +630,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -686,7 +673,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -749,7 +736,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -801,7 +787,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + + /// Transforms this `Read` instance to an [`Iterator`] over its bytes. +@@ -838,7 +823,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes where Self: Sized { + Bytes { inner: self } + } +@@ -873,7 +857,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain where Self: Sized { + Chain { first: self, second: next, done_first: false } + } +@@ -909,22 +892,52 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take where Self: Sized { + Take { inner: self, limit: limit } + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -937,14 +950,12 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -954,7 +965,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -967,11 +977,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -984,14 +992,12 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1002,13 +1008,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1022,21 +1026,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1090,7 +1091,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1139,7 +1139,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1150,7 +1149,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1178,7 +1176,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1211,7 +1208,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1263,7 +1259,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1319,7 +1314,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + } + +@@ -1349,7 +1343,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1365,7 +1358,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1403,7 +1395,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1442,7 +1433,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1454,29 +1444,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + -> Result { + let mut read = 0; +@@ -1556,7 +1543,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1597,7 +1584,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1619,7 +1605,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1675,7 +1660,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1734,7 +1718,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1775,7 +1758,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split where Self: Sized { + Split { buf: self, delim: byte } + } +@@ -1814,7 +1796,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines where Self: Sized { + Lines { buf: self } + } +@@ -1826,7 +1807,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -1852,7 +1832,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -1875,7 +1854,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -1902,13 +1880,11 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain") +@@ -1918,7 +1894,6 @@ impl fmt::Debug for Chain { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -1950,7 +1925,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -1977,7 +1952,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2012,7 +1986,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { self.limit } + + /// Sets the number of bytes that can be read before this instance will +@@ -2038,7 +2011,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2063,7 +2035,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2088,7 +2059,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2117,13 +2087,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2141,6 +2109,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + let reservation_size = cmp::min(self.limit, 32) as usize; + +@@ -2148,7 +2117,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2175,13 +2144,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2205,14 +2172,14 @@ impl Iterator for Bytes { + /// `BufRead`. Please see the documentation of `split()` for more details. + /// + /// [split]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2237,13 +2204,13 @@ impl Iterator for Split { + /// `BufRead`. Please see the documentation of `lines()` for more details. + /// + /// [lines]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 2e19edf..66294a3 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Write, Seek}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{Read, Write, BufRead, Seek}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index 33cc87e..75b8032 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, Read, Initializer, Write, ErrorKind, BufRead, IoSlice, IoSliceMut}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, Read, Initializer, Write, ErrorKind, IoSlice, IoSliceMut}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where R: Read, W: Write + { +@@ -70,7 +70,6 @@ pub fn copy(reader: &mut R, writer: &mut W) -> io::Result< + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { _priv: () } + + /// Constructs a new handle to an empty reader. +@@ -90,10 +89,8 @@ pub struct Empty { _priv: () } + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { Empty { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { Ok(0) } +@@ -103,7 +100,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(&[]) } +@@ -111,7 +109,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -124,7 +121,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { byte: u8 } + + /// Creates an instance of a reader that infinitely repeats one byte. +@@ -141,10 +137,8 @@ pub struct Repeat { byte: u8 } + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { Repeat { byte } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -169,7 +163,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -182,7 +175,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { _priv: () } + + /// Creates an instance of a writer which will successfully consume all data. +@@ -199,10 +191,8 @@ pub struct Sink { _priv: () } + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { Sink { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { Ok(buf.len()) } +@@ -217,7 +207,6 @@ impl Write for Sink { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/bc5669eef8c1d747e82694547fd57a1400a5afec.patch b/patches/bc5669eef8c1d747e82694547fd57a1400a5afec.patch new file mode 100644 index 0000000..33049f1 --- /dev/null +++ b/patches/bc5669eef8c1d747e82694547fd57a1400a5afec.patch @@ -0,0 +1,2078 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 987371f..d2af8b8 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,6 +1,7 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DEFAULT_BUF_SIZE}; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -42,7 +43,6 @@ use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DE + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -66,7 +66,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -87,7 +86,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -117,7 +115,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -140,7 +137,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -168,7 +164,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -191,7 +186,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -215,7 +209,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -233,7 +226,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -253,7 +245,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -309,7 +300,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -329,7 +319,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -342,7 +331,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index 65bc2fc..46cd6b8 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,9 +1,9 @@ +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; +-use crate::mem; ++use core::mem; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -65,7 +65,6 @@ use crate::mem; + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -87,7 +86,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -105,7 +103,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -200,7 +197,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -220,7 +216,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -238,7 +233,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -270,7 +264,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -294,7 +287,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -325,7 +317,6 @@ impl BufWriter { + /// assert_eq!(recovered_writer.len(), 0); + /// assert_eq!(&buffered_data.unwrap(), b"ata"); + /// ``` +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_raw_parts(mut self) -> (W, Result, WriterPanicked>) { + let buf = mem::take(&mut self.buf); + let buf = if !self.panicked { Ok(buf) } else { Err(WriterPanicked { buf }) }; +@@ -333,7 +324,6 @@ impl BufWriter { + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + /// Error returned for the buffered data from `BufWriter::into_raw_parts`, when the underlying + /// writer has previously panicked. Contains the (possibly partly written) buffered data. + /// +@@ -367,7 +357,6 @@ pub struct WriterPanicked { + impl WriterPanicked { + /// Returns the perhaps-unwritten data. Some of this data may have been written by the + /// panicking call(s) to the underlying writer, so simply writing it again is not a good idea. +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_inner(self) -> Vec { + self.buf + } +@@ -376,22 +365,12 @@ impl WriterPanicked { + "BufWriter inner writer panicked, what data remains unwritten is not known"; + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] +-impl error::Error for WriterPanicked { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- Self::DESCRIPTION +- } +-} +- +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Display for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + write!(f, "{}", Self::DESCRIPTION) + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Debug for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("WriterPanicked") +@@ -400,7 +379,6 @@ impl fmt::Debug for WriterPanicked { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -497,7 +475,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -510,7 +487,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -521,7 +497,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index d0c859d..a052adf 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index 6549781..0dc7440 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,7 +119,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } +@@ -143,7 +139,6 @@ impl IntoInnerError { + /// let err = into_inner_err.into_error(); + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_error(self) -> Error { + self.1 + } +@@ -167,28 +162,17 @@ impl IntoInnerError { + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// assert_eq!(recovered_writer.buffer(), b"t be actually written"); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_parts(self) -> (Error, W) { + (self.1, self.0) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/copy.rs b/copy.rs +index eb60df2..df99a47 100644 +--- a/copy.rs ++++ b/copy.rs +@@ -1,5 +1,6 @@ +-use super::{BufWriter, ErrorKind, Read, Result, Write, DEFAULT_BUF_SIZE}; +-use crate::mem::MaybeUninit; ++use super::{ErrorKind, Read, Result, Write, DEFAULT_BUF_SIZE}; ++#[cfg(feature = "collections")] use super::BufWriter; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,19 +40,12 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> Result + where + R: Read, + W: Write, + { +- cfg_if::cfg_if! { +- if #[cfg(any(target_os = "linux", target_os = "android"))] { +- crate::sys::kernel_copy::copy_spec(reader, writer) +- } else { +- generic_copy(reader, writer) +- } +- } ++ generic_copy(reader, writer) + } + + /// The userspace read-write-loop implementation of `io::copy` that is used when +@@ -76,6 +70,7 @@ impl BufferedCopySpec for W { + } + } + ++#[cfg(feature = "collections")] + impl BufferedCopySpec for BufWriter { + fn copy_to(reader: &mut R, writer: &mut Self) -> Result { + if writer.capacity() < DEFAULT_BUF_SIZE { +diff --git a/cursor.rs b/cursor.rs +index bbee2cc..dc75216 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,8 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,8 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn get_ref(&self) -> &T { + &self.inner + } +@@ -152,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -176,8 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn position(&self) -> u64 { + self.pos + } +@@ -199,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -245,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -274,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -285,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -326,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -354,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -366,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -389,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -410,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -431,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 00bf8b9..5c0e7cd 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -216,7 +222,6 @@ impl BufRead for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -279,6 +284,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -288,7 +294,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -310,7 +316,6 @@ impl BufRead for &[u8] { + /// If the number of bytes to be written exceeds the size of the slice, write operations will + /// return short writes: ultimately, `Ok(0)`; in this situation, `write_all` returns an error of + /// kind `ErrorKind::WriteZero`. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -356,7 +361,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 2291498..d1a519a 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -246,58 +246,48 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::copy::copy; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[unstable(feature = "internal_output_capture", issue = "none")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::set_output_capture; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + pub(crate) mod copy; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -324,6 +314,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -351,10 +342,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -504,7 +497,6 @@ pub(crate) fn default_read_exact(this: &mut R, mut buf: &mut [ + /// [`&str`]: prim@str + /// [`std::io`]: self + /// [`File`]: crate::fs::File +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -575,7 +567,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -587,7 +578,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -600,7 +590,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -624,7 +613,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -676,7 +664,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -719,7 +707,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -783,7 +771,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, buf: &mut [u8]) -> Result<()> { + default_read_exact(self, buf) + } +@@ -822,7 +809,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -859,7 +845,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -897,7 +882,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -936,7 +920,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -986,29 +969,71 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +-#[unstable(feature = "io_read_to_string", issue = "80218")] ++#[cfg(feature="collections")] + pub fn read_to_string(reader: &mut R) -> Result { + let mut buf = String::new(); + reader.read_to_string(&mut buf)?; + Ok(buf) + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1021,10 +1046,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1059,7 +1083,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1083,7 +1106,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1093,7 +1115,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1106,18 +1127,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1130,10 +1147,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1167,7 +1183,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1191,7 +1206,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1202,13 +1216,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1222,21 +1234,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1290,7 +1299,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1337,7 +1345,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1350,7 +1357,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1365,7 +1371,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1393,7 +1398,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1427,7 +1431,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1489,7 +1492,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1542,7 +1544,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1598,7 +1599,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1633,7 +1633,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1647,7 +1646,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1684,7 +1682,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_stream_len", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1721,7 +1718,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "seek_convenience", since = "1.51.0")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1731,29 +1727,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1829,7 +1822,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1870,7 +1863,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1892,7 +1884,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1949,7 +1940,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -2012,7 +2002,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2050,7 +2039,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2087,7 +2075,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2102,7 +2089,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2128,7 +2114,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2151,7 +2136,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2178,20 +2162,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2219,7 +2200,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2244,7 +2225,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2277,7 +2257,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2305,7 +2284,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2330,7 +2308,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2355,7 +2332,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2384,13 +2360,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2408,6 +2382,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2416,7 +2391,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2443,13 +2418,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2473,14 +2446,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2505,13 +2478,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index d806431..6b9791a 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index e43ce4c..e1f6fbc 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,14 +3,14 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write}; ++use core::fmt; ++use crate::io::{self, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; + + /// A reader which is always at EOF. + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -30,13 +30,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -48,7 +45,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -58,7 +56,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "empty_seek", since = "1.51.0")] + impl Seek for Empty { + fn seek(&mut self, _pos: SeekFrom) -> io::Result { + Ok(0) +@@ -73,7 +70,6 @@ impl Seek for Empty { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -84,7 +80,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -103,13 +98,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -139,7 +131,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -150,7 +141,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -171,13 +161,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -201,7 +188,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -225,7 +211,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/bdaa76cfde64d06bb93c1f9102a0312d84cd0983.patch b/patches/bdaa76cfde64d06bb93c1f9102a0312d84cd0983.patch new file mode 100644 index 0000000..58657b0 --- /dev/null +++ b/patches/bdaa76cfde64d06bb93c1f9102a0312d84cd0983.patch @@ -0,0 +1,1986 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 16c18d6..f392e3c 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,6 +1,7 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DEFAULT_BUF_SIZE}; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -42,7 +43,6 @@ use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DE + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -66,7 +66,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -87,7 +86,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -117,7 +115,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -140,7 +137,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -168,7 +164,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -191,7 +186,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -215,7 +209,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -233,7 +226,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -253,7 +245,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -295,7 +286,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -315,7 +305,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -328,7 +317,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index 067ed6b..47869a7 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,7 +1,8 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -63,7 +64,6 @@ use crate::io::{ + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -85,7 +85,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -103,7 +102,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -198,7 +196,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -218,7 +215,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -236,7 +232,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -256,7 +251,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -280,7 +274,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -289,7 +282,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -353,7 +345,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -366,7 +357,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -377,7 +367,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index a80d08d..20bd401 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index f9caeaf..c21de5c 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,28 +119,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/copy.rs b/copy.rs +index b88bca2..7593702 100644 +--- a/copy.rs ++++ b/copy.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, ErrorKind, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,19 +39,12 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, + W: Write, + { +- cfg_if::cfg_if! { +- if #[cfg(any(target_os = "linux", target_os = "android"))] { +- crate::sys::kernel_copy::copy_spec(reader, writer) +- } else { +- generic_copy(reader, writer) +- } +- } ++ generic_copy(reader, writer) + } + + /// The general read-write-loop implementation of +diff --git a/cursor.rs b/cursor.rs +index bbee2cc..dc75216 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,8 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,8 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn get_ref(&self) -> &T { + &self.inner + } +@@ -152,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -176,8 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn position(&self) -> u64 { + self.pos + } +@@ -199,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -245,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -274,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -285,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -326,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -354,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -366,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -389,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -410,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -431,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 6b3c86c..093d9c3 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -216,7 +222,6 @@ impl BufRead for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -279,6 +284,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -288,7 +294,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -306,7 +312,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -352,7 +357,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index dfbf6c3..7437b18 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -247,58 +247,48 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::copy::copy; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[unstable(feature = "internal_output_capture", issue = "none")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::set_output_capture; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + pub(crate) mod copy; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -325,6 +315,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -352,10 +343,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -489,7 +482,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -560,7 +552,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -572,7 +563,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -585,7 +575,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -609,7 +598,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -661,7 +649,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -704,7 +692,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -768,7 +756,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -822,7 +809,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -859,7 +845,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -897,7 +882,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -936,7 +920,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -945,22 +928,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -973,10 +998,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1011,7 +1035,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1035,7 +1058,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1045,7 +1067,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1058,18 +1079,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1082,10 +1099,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1119,7 +1135,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1143,7 +1158,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1154,13 +1168,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1174,21 +1186,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1242,7 +1251,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1289,7 +1297,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1302,7 +1309,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1317,7 +1323,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1345,7 +1350,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1379,7 +1383,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1441,7 +1444,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1494,7 +1496,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1550,7 +1551,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1585,7 +1585,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1599,7 +1598,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1636,7 +1634,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1674,7 +1671,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1684,29 +1680,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1782,7 +1775,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1823,7 +1816,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1845,7 +1837,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1902,7 +1893,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1965,7 +1955,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2004,7 +1993,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2041,7 +2029,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2056,7 +2043,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2082,7 +2068,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2105,7 +2090,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2132,20 +2116,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2173,7 +2154,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2198,7 +2179,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2231,7 +2211,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2259,7 +2238,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2284,7 +2262,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2309,7 +2286,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2338,13 +2314,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2362,6 +2336,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2370,7 +2345,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2397,13 +2372,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2427,14 +2400,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2459,13 +2432,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index db84545..8e88c3d 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,14 +3,14 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, Initializer, IoSlice, IoSliceMut, Read, Write}; ++use core::fmt; ++use crate::io::{self, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; + + /// A reader which is always at EOF. + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -30,13 +30,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -48,7 +45,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -58,7 +56,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -69,7 +66,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -88,13 +84,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -124,7 +117,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -135,7 +127,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -156,13 +147,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -186,7 +174,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -210,7 +197,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/c26a8bbd6d0e7bbfa2891934a1af2934cab3b6bb.patch b/patches/c26a8bbd6d0e7bbfa2891934a1af2934cab3b6bb.patch new file mode 100644 index 0000000..8a7f0fa --- /dev/null +++ b/patches/c26a8bbd6d0e7bbfa2891934a1af2934cab3b6bb.patch @@ -0,0 +1,2078 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 987371f..d2af8b8 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,6 +1,7 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DEFAULT_BUF_SIZE}; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -42,7 +43,6 @@ use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DE + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -66,7 +66,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -87,7 +86,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -117,7 +115,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -140,7 +137,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -168,7 +164,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -191,7 +186,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -215,7 +209,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -233,7 +226,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -253,7 +245,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -309,7 +300,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -329,7 +319,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -342,7 +331,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index 65bc2fc..46cd6b8 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,9 +1,9 @@ +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; +-use crate::mem; ++use core::mem; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -65,7 +65,6 @@ use crate::mem; + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -87,7 +86,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -105,7 +103,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -200,7 +197,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -220,7 +216,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -238,7 +233,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -270,7 +264,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -294,7 +287,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -325,7 +317,6 @@ impl BufWriter { + /// assert_eq!(recovered_writer.len(), 0); + /// assert_eq!(&buffered_data.unwrap(), b"ata"); + /// ``` +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_raw_parts(mut self) -> (W, Result, WriterPanicked>) { + let buf = mem::take(&mut self.buf); + let buf = if !self.panicked { Ok(buf) } else { Err(WriterPanicked { buf }) }; +@@ -333,7 +324,6 @@ impl BufWriter { + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + /// Error returned for the buffered data from `BufWriter::into_raw_parts`, when the underlying + /// writer has previously panicked. Contains the (possibly partly written) buffered data. + /// +@@ -367,7 +357,6 @@ pub struct WriterPanicked { + impl WriterPanicked { + /// Returns the perhaps-unwritten data. Some of this data may have been written by the + /// panicking call(s) to the underlying writer, so simply writing it again is not a good idea. +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_inner(self) -> Vec { + self.buf + } +@@ -376,22 +365,12 @@ impl WriterPanicked { + "BufWriter inner writer panicked, what data remains unwritten is not known"; + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] +-impl error::Error for WriterPanicked { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- Self::DESCRIPTION +- } +-} +- +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Display for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + write!(f, "{}", Self::DESCRIPTION) + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Debug for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("WriterPanicked") +@@ -400,7 +379,6 @@ impl fmt::Debug for WriterPanicked { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -497,7 +475,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -510,7 +487,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -521,7 +497,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index d0c859d..a052adf 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index 6549781..0dc7440 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,7 +119,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } +@@ -143,7 +139,6 @@ impl IntoInnerError { + /// let err = into_inner_err.into_error(); + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_error(self) -> Error { + self.1 + } +@@ -167,28 +162,17 @@ impl IntoInnerError { + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// assert_eq!(recovered_writer.buffer(), b"t be actually written"); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_parts(self) -> (Error, W) { + (self.1, self.0) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/copy.rs b/copy.rs +index 3780f20..9c52ecc 100644 +--- a/copy.rs ++++ b/copy.rs +@@ -1,5 +1,6 @@ +-use super::{BufWriter, ErrorKind, Read, Result, Write, DEFAULT_BUF_SIZE}; +-use crate::mem::MaybeUninit; ++use super::{ErrorKind, Read, Result, Write, DEFAULT_BUF_SIZE}; ++#[cfg(feature = "collections")] use super::BufWriter; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,19 +40,12 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> Result + where + R: Read, + W: Write, + { +- cfg_if::cfg_if! { +- if #[cfg(any(target_os = "linux", target_os = "android"))] { +- crate::sys::kernel_copy::copy_spec(reader, writer) +- } else { +- generic_copy(reader, writer) +- } +- } ++ generic_copy(reader, writer) + } + + /// The userspace read-write-loop implementation of `io::copy` that is used when +@@ -76,6 +70,7 @@ impl BufferedCopySpec for W { + } + } + ++#[cfg(feature = "collections")] + impl BufferedCopySpec for BufWriter { + fn copy_to(reader: &mut R, writer: &mut Self) -> Result { + if writer.capacity() < DEFAULT_BUF_SIZE { +diff --git a/cursor.rs b/cursor.rs +index bbee2cc..dc75216 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,8 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,8 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn get_ref(&self) -> &T { + &self.inner + } +@@ -152,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -176,8 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn position(&self) -> u64 { + self.pos + } +@@ -199,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -245,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -274,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -285,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -326,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -354,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -366,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -389,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -410,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -431,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 00bf8b9..5c0e7cd 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -216,7 +222,6 @@ impl BufRead for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -279,6 +284,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -288,7 +294,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -310,7 +316,6 @@ impl BufRead for &[u8] { + /// If the number of bytes to be written exceeds the size of the slice, write operations will + /// return short writes: ultimately, `Ok(0)`; in this situation, `write_all` returns an error of + /// kind `ErrorKind::WriteZero`. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -356,7 +361,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index db3b0e2..6e3a4c5 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -246,58 +246,48 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::copy::copy; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[unstable(feature = "internal_output_capture", issue = "none")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::set_output_capture; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + pub(crate) mod copy; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -324,6 +314,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -351,10 +342,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -505,7 +498,6 @@ pub(crate) fn default_read_exact(this: &mut R, mut buf: &mut [ + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -576,7 +568,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -588,7 +579,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -601,7 +591,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -625,7 +614,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -677,7 +665,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -720,7 +708,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -784,7 +772,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, buf: &mut [u8]) -> Result<()> { + default_read_exact(self, buf) + } +@@ -823,7 +810,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -860,7 +846,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -898,7 +883,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -937,7 +921,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -987,29 +970,71 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +-#[unstable(feature = "io_read_to_string", issue = "80218")] ++#[cfg(feature="collections")] + pub fn read_to_string(reader: &mut R) -> Result { + let mut buf = String::new(); + reader.read_to_string(&mut buf)?; + Ok(buf) + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1022,10 +1047,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1060,7 +1084,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1084,7 +1107,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1094,7 +1116,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1107,18 +1128,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1131,10 +1148,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1168,7 +1184,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1192,7 +1207,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1203,13 +1217,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1223,21 +1235,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1291,7 +1300,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1338,7 +1346,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1351,7 +1358,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1366,7 +1372,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1394,7 +1399,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1428,7 +1432,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1490,7 +1493,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1543,7 +1545,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1599,7 +1600,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1634,7 +1634,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1648,7 +1647,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1685,7 +1683,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_stream_len", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1722,7 +1719,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "seek_convenience", since = "1.51.0")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1732,29 +1728,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1830,7 +1823,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1871,7 +1864,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1893,7 +1885,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1950,7 +1941,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -2013,7 +2003,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2051,7 +2040,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2088,7 +2076,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2103,7 +2090,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2129,7 +2115,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2152,7 +2137,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2179,20 +2163,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2220,7 +2201,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2245,7 +2226,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2278,7 +2258,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2306,7 +2285,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2331,7 +2309,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2356,7 +2333,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2385,13 +2361,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2409,6 +2383,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2417,7 +2392,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2444,13 +2419,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2474,14 +2447,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2506,13 +2479,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index d806431..6b9791a 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index e43ce4c..e1f6fbc 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,14 +3,14 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write}; ++use core::fmt; ++use crate::io::{self, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; + + /// A reader which is always at EOF. + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -30,13 +30,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -48,7 +45,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -58,7 +56,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "empty_seek", since = "1.51.0")] + impl Seek for Empty { + fn seek(&mut self, _pos: SeekFrom) -> io::Result { + Ok(0) +@@ -73,7 +70,6 @@ impl Seek for Empty { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -84,7 +80,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -103,13 +98,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -139,7 +131,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -150,7 +141,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -171,13 +161,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -201,7 +188,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -225,7 +211,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/c5d18600ef3c5e795c4133cfd91a1df088f2252e.patch b/patches/c5d18600ef3c5e795c4133cfd91a1df088f2252e.patch new file mode 100644 index 0000000..1a579ce --- /dev/null +++ b/patches/c5d18600ef3c5e795c4133cfd91a1df088f2252e.patch @@ -0,0 +1,1761 @@ +diff --git a/buffered.rs b/buffered.rs +index aaf628e..259eba3 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,13 +1,13 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, Initializer, DEFAULT_BUF_SIZE, Error, ErrorKind, SeekFrom, IoSlice, + IoSliceMut}; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -47,7 +47,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -71,7 +70,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -92,7 +90,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -127,7 +124,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { &self.inner } + + /// Gets a mutable reference to the underlying reader. +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { &mut self.inner } + + /// Returns a reference to the internally buffered data. +@@ -172,7 +167,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -195,7 +189,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { self.inner } + + /// Invalidates all data in the internal buffer. +@@ -211,7 +204,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -231,7 +223,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -269,7 +260,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -289,7 +279,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader where R: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufReader") +@@ -299,7 +288,6 @@ impl fmt::Debug for BufReader where R: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -408,7 +396,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -443,7 +430,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -458,7 +444,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -476,7 +461,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { + inner: Some(inner), +@@ -525,7 +509,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.as_ref().unwrap() } + + /// Gets a mutable reference to the underlying writer. +@@ -543,7 +526,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.as_mut().unwrap() } + + /// Returns a reference to the internally buffered data. +@@ -559,7 +541,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -583,7 +564,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -592,7 +572,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -628,7 +607,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufWriter") +@@ -638,7 +616,6 @@ impl fmt::Debug for BufWriter where W: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -648,7 +625,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -687,7 +663,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { &self.1 } + + /// Returns the buffered writer instance which generated the error. +@@ -720,23 +695,13 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { self.0 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { iie.1 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -807,7 +772,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -828,7 +792,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -849,7 +812,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { + inner: BufWriter::with_capacity(capacity, inner), +@@ -873,7 +835,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.get_ref() } + + /// Gets a mutable reference to the underlying writer. +@@ -896,7 +857,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.get_mut() } + + /// Unwraps this `LineWriter`, returning the underlying writer. +@@ -922,7 +882,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { +@@ -933,7 +892,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -978,7 +936,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("LineWriter") +diff --git a/cursor.rs b/cursor.rs +index a94176e..7768d39 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Initializer, SeekFrom, Error, ErrorKind, IoSlice, IoSliceMut}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { self.inner } + + /// Gets a reference to the underlying value in this cursor. +@@ -128,7 +125,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { &self.inner } + + /// Gets a mutable reference to the underlying value in this cursor. +@@ -147,7 +143,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { &mut self.inner } + + /// Returns the current position of this cursor. +@@ -169,7 +164,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { self.pos } + + /// Sets the position of this cursor. +@@ -189,11 +183,9 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { self.pos = pos; } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor where T: AsRef<[u8]> { + fn seek(&mut self, style: SeekFrom) -> io::Result { + let (base_pos, offset) = match style { +@@ -222,10 +214,9 @@ impl io::Seek for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor where T: AsRef<[u8]> { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -244,7 +235,7 @@ impl Read for Cursor where T: AsRef<[u8]> { + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -255,12 +246,16 @@ impl Read for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor where T: AsRef<[u8]> { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++impl Cursor where T: AsRef<[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor where T: AsRef<[u8]> { ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { self.get_buf() } + fn consume(&mut self, amt: usize) { self.pos += amt as u64; } + } + +@@ -292,6 +287,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new(ErrorKind::InvalidInput, +@@ -318,6 +314,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -331,7 +328,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -347,7 +343,7 @@ impl Write for Cursor<&mut [u8]> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -361,7 +357,7 @@ impl Write for Cursor<&mut Vec> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -375,8 +371,8 @@ impl Write for Cursor> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index c29a68e..c94d8c5 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,13 @@ +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; +-use crate::convert::From; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++use core::convert::Into; ++use core::fmt; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++use core::result; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; ++use core::convert::From; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +43,6 @@ use crate::convert::From; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +56,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +69,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +90,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +130,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +142,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +156,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +186,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -245,14 +230,13 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error +- where E: Into> ++ where E: Into + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { + repr: Repr::Custom(Box::new(Custom { + kind, +@@ -261,24 +245,6 @@ impl Error { + } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -304,7 +270,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -335,7 +300,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -369,12 +333,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error+Send+Sync+'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -440,12 +403,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error+Send+Sync+'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -474,8 +436,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -501,10 +462,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -516,22 +476,18 @@ impl fmt::Debug for Repr { + match *self { + Repr::Os(code) => + fmt.debug_struct("Os") +- .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)).finish(), ++ .field("code", &code).finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), + } + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -539,33 +495,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index c959f2d..b645bc8 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,13 +1,15 @@ +-use crate::cmp; +-use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, BufRead, Error, ErrorKind, +- IoSliceMut, IoSlice}; +-use crate::fmt; +-use crate::mem; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++use core::cmp; ++use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, Error, ErrorKind, IoSliceMut, IoSlice}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::fmt; ++use core::mem; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -24,11 +26,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -39,7 +43,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -62,12 +65,11 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -86,7 +88,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -103,11 +105,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -118,7 +122,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -141,12 +145,12 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -186,7 +190,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -245,6 +248,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -254,7 +258,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(*self) } +@@ -268,7 +272,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -307,7 +310,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index a8d4d11..39da12d 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,50 +257,38 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::slice; +-use crate::str; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(feature="collections")] use collections::string::String; ++use core::str; ++#[cfg(feature="collections")] use collections::vec::Vec; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::slice; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++ ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Result, Error, ErrorKind}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, sink, Sink, empty, Empty, repeat, Repeat}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stdin, stdout, stderr, Stdin, Stdout, Stderr}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StdoutLock, StderrLock, StdinLock}; +-#[unstable(feature = "print_internals", issue = "0")] +-pub use self::stdio::{_print, _eprint}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; + + pub mod prelude; +-mod buffered; ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + mod util; +-mod stdio; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { buf: &'a mut Vec, len: usize } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { self.buf.set_len(self.len); } +@@ -325,6 +313,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where F: FnOnce(&mut Vec) -> Result + { +@@ -352,10 +341,12 @@ fn append_to_string(buf: &mut String, f: F) -> Result + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation(r: &mut R, + buf: &mut Vec, + reservation_size: usize) -> Result +@@ -484,7 +475,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -552,7 +542,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -563,7 +552,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -590,7 +578,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -643,7 +630,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -686,7 +673,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -749,7 +736,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -801,7 +787,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + + /// Transforms this `Read` instance to an [`Iterator`] over its bytes. +@@ -838,7 +823,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes where Self: Sized { + Bytes { inner: self } + } +@@ -873,7 +857,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain where Self: Sized { + Chain { first: self, second: next, done_first: false } + } +@@ -909,22 +892,52 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take where Self: Sized { + Take { inner: self, limit: limit } + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -937,14 +950,12 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -954,7 +965,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -967,11 +977,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -984,14 +992,12 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1002,13 +1008,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1022,21 +1026,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1090,7 +1091,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1139,7 +1139,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1150,7 +1149,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1178,7 +1176,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1211,7 +1208,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1263,7 +1259,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1319,7 +1314,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + } + +@@ -1349,7 +1343,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1365,7 +1358,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1403,7 +1395,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1442,7 +1433,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1454,29 +1444,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + -> Result { + let mut read = 0; +@@ -1556,7 +1543,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1597,7 +1584,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1619,7 +1605,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1675,7 +1660,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1734,7 +1718,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1775,7 +1758,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split where Self: Sized { + Split { buf: self, delim: byte } + } +@@ -1814,7 +1796,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines where Self: Sized { + Lines { buf: self } + } +@@ -1826,7 +1807,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -1852,7 +1832,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -1875,7 +1854,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -1902,13 +1880,11 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain") +@@ -1918,7 +1894,6 @@ impl fmt::Debug for Chain { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -1950,7 +1925,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -1977,7 +1952,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2012,7 +1986,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { self.limit } + + /// Sets the number of bytes that can be read before this instance will +@@ -2038,7 +2011,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2063,7 +2035,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2088,7 +2059,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2117,13 +2087,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2141,6 +2109,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + let reservation_size = cmp::min(self.limit, 32) as usize; + +@@ -2148,7 +2117,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2175,13 +2144,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2205,14 +2172,14 @@ impl Iterator for Bytes { + /// `BufRead`. Please see the documentation of `split()` for more details. + /// + /// [split]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2237,13 +2204,13 @@ impl Iterator for Split { + /// `BufRead`. Please see the documentation of `lines()` for more details. + /// + /// [lines]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 2e19edf..66294a3 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Write, Seek}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{Read, Write, BufRead, Seek}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index 2bfd3e4..737edb0 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, Read, Initializer, Write, ErrorKind, BufRead, IoSlice, IoSliceMut}; +-use crate::mem; ++use core::fmt; ++use crate::io::{self, Read, Initializer, Write, ErrorKind, IoSlice, IoSliceMut}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where R: Read, W: Write + { +@@ -69,7 +69,6 @@ pub fn copy(reader: &mut R, writer: &mut W) -> io::Result< + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { _priv: () } + + /// Constructs a new handle to an empty reader. +@@ -89,10 +88,8 @@ pub struct Empty { _priv: () } + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { Empty { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { Ok(0) } +@@ -102,7 +99,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(&[]) } +@@ -110,7 +108,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -123,7 +120,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { byte: u8 } + + /// Creates an instance of a reader that infinitely repeats one byte. +@@ -140,10 +136,8 @@ pub struct Repeat { byte: u8 } + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { Repeat { byte } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -168,7 +162,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -181,7 +174,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { _priv: () } + + /// Creates an instance of a writer which will successfully consume all data. +@@ -198,10 +190,8 @@ pub struct Sink { _priv: () } + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { Sink { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { Ok(buf.len()) } +@@ -216,7 +206,6 @@ impl Write for Sink { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/c9290dceee2cb6b882b26ec6e294560e51ef0853.patch b/patches/c9290dceee2cb6b882b26ec6e294560e51ef0853.patch new file mode 100644 index 0000000..9e043b4 --- /dev/null +++ b/patches/c9290dceee2cb6b882b26ec6e294560e51ef0853.patch @@ -0,0 +1,1848 @@ +diff --git a/buffered.rs b/buffered.rs +index 6739d44..7898006 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68558")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -222,7 +215,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -240,7 +232,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -260,7 +251,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -298,7 +288,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -318,7 +307,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -331,7 +319,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -442,7 +429,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -477,7 +463,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -492,7 +477,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -510,7 +494,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -557,7 +540,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -577,7 +559,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -595,7 +576,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -616,7 +596,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68558")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -640,7 +619,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -649,7 +627,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -685,7 +662,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -698,7 +674,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -708,7 +683,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -747,7 +721,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -782,28 +755,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -874,7 +836,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -895,7 +856,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -916,7 +876,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -937,7 +896,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -962,7 +920,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -990,7 +947,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -998,7 +954,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1104,7 +1059,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index 9787cbb..1cf83d3 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -268,7 +259,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -279,15 +270,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -320,6 +320,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -348,6 +349,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -360,7 +362,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -378,7 +379,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -394,7 +395,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -410,8 +411,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index 3b55d9b..c754d1f 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -432,12 +396,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -466,8 +429,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -493,10 +455,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -509,8 +470,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -518,13 +477,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -532,34 +489,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index b7f82e6..c857f83 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -25,11 +29,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -40,7 +46,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -67,14 +72,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -97,7 +101,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -114,11 +118,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -129,7 +135,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -156,14 +162,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -207,7 +213,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -265,6 +270,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -274,7 +280,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -292,7 +298,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -333,7 +338,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 67b382c..f8ccb5e 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,53 +257,43 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -330,6 +320,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -357,10 +348,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -496,7 +489,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -564,7 +556,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -575,7 +566,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -602,7 +592,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -655,7 +644,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -698,7 +687,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -761,7 +750,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -815,7 +803,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -857,7 +844,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -895,7 +881,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -934,7 +919,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -943,16 +927,59 @@ pub trait Read { + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -965,10 +992,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1003,7 +1029,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1027,7 +1052,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1037,7 +1061,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1050,11 +1073,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1067,10 +1088,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1104,7 +1124,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1128,7 +1147,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1139,13 +1157,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1159,21 +1175,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1227,7 +1240,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1276,7 +1288,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1287,7 +1298,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1315,7 +1325,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1350,7 +1359,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1403,7 +1411,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1459,7 +1466,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1494,7 +1500,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1510,7 +1515,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1548,7 +1552,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1587,7 +1590,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1599,29 +1601,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1700,7 +1699,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1741,7 +1740,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1763,7 +1761,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1819,7 +1816,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1878,7 +1874,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1919,7 +1914,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -1961,7 +1955,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -1976,7 +1969,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2002,7 +1994,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2025,7 +2016,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2052,20 +2042,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2093,7 +2080,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2118,7 +2105,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2153,7 +2139,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2181,7 +2166,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2206,7 +2190,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2231,7 +2214,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2260,13 +2242,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2284,6 +2264,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2292,7 +2273,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2319,13 +2300,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2349,14 +2328,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2381,13 +2360,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b09161b..e52119e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -185,7 +179,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -217,12 +209,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -241,7 +231,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/c9e5e6a53aef5cd1b939ecfa18f56bdf5bf0451c.patch b/patches/c9e5e6a53aef5cd1b939ecfa18f56bdf5bf0451c.patch new file mode 100644 index 0000000..efa02cc --- /dev/null +++ b/patches/c9e5e6a53aef5cd1b939ecfa18f56bdf5bf0451c.patch @@ -0,0 +1,1910 @@ +diff --git a/buffered.rs b/buffered.rs +index 97c4b87..ae26453 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -3,15 +3,15 @@ + #[cfg(test)] + mod tests; + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -52,7 +52,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -76,7 +75,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -97,7 +95,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -127,7 +124,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -150,7 +146,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -178,7 +173,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -201,7 +195,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -225,7 +218,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -243,7 +235,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -263,7 +254,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -305,7 +295,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -325,7 +314,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -338,7 +326,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -492,7 +479,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: Write::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: Write::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -527,7 +513,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -542,7 +527,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -560,7 +544,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -655,7 +638,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -675,7 +657,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -693,7 +674,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -713,7 +693,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -737,7 +716,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -746,7 +724,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -810,7 +787,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -823,7 +799,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -834,7 +809,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -874,7 +848,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -909,28 +882,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -1267,7 +1229,6 @@ impl<'a, W: Write> Write for LineWriterShim<'a, W> { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -1287,7 +1248,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -1308,7 +1268,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -1329,7 +1288,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -1354,7 +1312,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -1382,7 +1339,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner + .into_inner() +@@ -1390,7 +1346,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -1421,7 +1376,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index 5733735..0fdd84a 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,7 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -111,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -129,7 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -150,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -196,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -242,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -271,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -282,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -323,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -351,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -363,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -386,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -407,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -428,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index e09e7ba..126a710 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -230,7 +236,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -293,6 +298,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -302,7 +308,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -320,7 +326,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -366,7 +371,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index d9d0380..e647c6b 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -247,55 +247,46 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -322,6 +313,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -349,10 +341,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -486,7 +480,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -557,7 +550,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -569,7 +561,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -582,7 +573,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -606,7 +596,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -658,7 +647,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -701,7 +690,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -765,7 +754,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -819,7 +807,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -856,7 +843,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -894,7 +880,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -933,7 +918,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -942,22 +926,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -970,10 +996,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1008,7 +1033,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1032,7 +1056,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1042,7 +1065,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1055,18 +1077,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1079,10 +1097,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1116,7 +1133,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1140,7 +1156,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1151,13 +1166,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1171,21 +1184,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1239,7 +1249,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1286,7 +1295,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1299,7 +1307,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1314,7 +1321,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1342,7 +1348,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1376,7 +1381,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1438,7 +1442,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1491,7 +1494,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1547,7 +1549,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1582,7 +1583,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1596,7 +1596,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1633,7 +1632,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1671,7 +1669,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1681,29 +1678,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1779,7 +1773,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1820,7 +1814,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1842,7 +1835,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1899,7 +1891,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1962,7 +1953,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2001,7 +1991,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2038,7 +2027,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2053,7 +2041,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2079,7 +2066,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2102,7 +2088,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2129,20 +2114,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2170,7 +2152,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2195,7 +2177,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2228,7 +2209,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2256,7 +2236,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2281,7 +2260,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2306,7 +2284,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2335,13 +2312,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2359,6 +2334,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2367,7 +2343,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2394,13 +2370,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2424,14 +2398,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2456,13 +2430,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index dc05b96..aa7ee35 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,9 +3,10 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -45,7 +46,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -81,7 +81,6 @@ where + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -101,12 +100,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -118,7 +115,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -128,7 +126,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -139,7 +136,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -158,12 +154,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -193,7 +187,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -204,7 +197,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -225,12 +217,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -254,7 +244,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -278,7 +267,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/ce48709405270cae2dfdf99d9a8d57a4f672ad34.patch b/patches/ce48709405270cae2dfdf99d9a8d57a4f672ad34.patch new file mode 100644 index 0000000..e3a0c98 --- /dev/null +++ b/patches/ce48709405270cae2dfdf99d9a8d57a4f672ad34.patch @@ -0,0 +1,2010 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 16c18d6..f392e3c 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,6 +1,7 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DEFAULT_BUF_SIZE}; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -42,7 +43,6 @@ use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DE + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -66,7 +66,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -87,7 +86,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -117,7 +115,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -140,7 +137,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -168,7 +164,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -191,7 +186,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -215,7 +209,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -233,7 +226,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -253,7 +245,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -295,7 +286,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -315,7 +305,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -328,7 +317,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index 3b33998..d20db36 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,7 +1,8 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -63,7 +64,6 @@ use crate::io::{ + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -85,7 +85,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -103,7 +102,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -198,7 +196,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -218,7 +215,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -236,7 +232,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -256,7 +251,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -280,7 +274,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -289,7 +282,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -386,7 +378,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -399,7 +390,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -410,7 +400,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index d0c859d..a052adf 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index 6549781..0dc7440 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,7 +119,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } +@@ -143,7 +139,6 @@ impl IntoInnerError { + /// let err = into_inner_err.into_error(); + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_error(self) -> Error { + self.1 + } +@@ -167,28 +162,17 @@ impl IntoInnerError { + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// assert_eq!(recovered_writer.buffer(), b"t be actually written"); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_parts(self) -> (Error, W) { + (self.1, self.0) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/copy.rs b/copy.rs +index b88bca2..7593702 100644 +--- a/copy.rs ++++ b/copy.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, ErrorKind, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,19 +39,12 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, + W: Write, + { +- cfg_if::cfg_if! { +- if #[cfg(any(target_os = "linux", target_os = "android"))] { +- crate::sys::kernel_copy::copy_spec(reader, writer) +- } else { +- generic_copy(reader, writer) +- } +- } ++ generic_copy(reader, writer) + } + + /// The general read-write-loop implementation of +diff --git a/cursor.rs b/cursor.rs +index bbee2cc..dc75216 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,8 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,8 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn get_ref(&self) -> &T { + &self.inner + } +@@ -152,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -176,8 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn position(&self) -> u64 { + self.pos + } +@@ -199,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -245,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -274,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -285,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -326,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -354,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -366,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -389,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -410,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -431,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 00bf8b9..5c0e7cd 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -216,7 +222,6 @@ impl BufRead for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -279,6 +284,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -288,7 +294,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -310,7 +316,6 @@ impl BufRead for &[u8] { + /// If the number of bytes to be written exceeds the size of the slice, write operations will + /// return short writes: ultimately, `Ok(0)`; in this situation, `write_all` returns an error of + /// kind `ErrorKind::WriteZero`. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -356,7 +361,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 3f5b7c0..59ea33a 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -246,58 +246,48 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::copy::copy; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[unstable(feature = "internal_output_capture", issue = "none")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::set_output_capture; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + pub(crate) mod copy; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -324,6 +314,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -351,10 +342,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -486,7 +479,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -557,7 +549,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -569,7 +560,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -582,7 +572,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -606,7 +595,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -658,7 +646,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -701,7 +689,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -765,7 +753,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -819,7 +806,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -856,7 +842,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -894,7 +879,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -933,7 +917,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -983,29 +966,71 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +-#[unstable(feature = "io_read_to_string", issue = "80218")] ++#[cfg(feature="collections")] + pub fn read_to_string(reader: &mut R) -> Result { + let mut buf = String::new(); + reader.read_to_string(&mut buf)?; + Ok(buf) + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1018,10 +1043,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1056,7 +1080,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1080,7 +1103,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1090,7 +1112,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1103,18 +1124,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1127,10 +1144,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1164,7 +1180,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1188,7 +1203,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1199,13 +1213,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1219,21 +1231,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1287,7 +1296,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1334,7 +1342,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1347,7 +1354,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1362,7 +1368,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1390,7 +1395,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1424,7 +1428,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1486,7 +1489,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1539,7 +1541,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1595,7 +1596,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1630,7 +1630,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1644,7 +1643,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1681,7 +1679,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1719,7 +1716,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1729,29 +1725,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1827,7 +1820,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1868,7 +1861,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1890,7 +1882,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1947,7 +1938,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -2010,7 +2000,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2048,7 +2037,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2085,7 +2073,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2100,7 +2087,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2126,7 +2112,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2149,7 +2134,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2176,20 +2160,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2217,7 +2198,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2242,7 +2223,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2275,7 +2255,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2303,7 +2282,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2328,7 +2306,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2353,7 +2330,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2382,13 +2358,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2406,6 +2380,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2414,7 +2389,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2441,13 +2416,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2471,14 +2444,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2503,13 +2476,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index db84545..8e88c3d 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,14 +3,14 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, Initializer, IoSlice, IoSliceMut, Read, Write}; ++use core::fmt; ++use crate::io::{self, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; + + /// A reader which is always at EOF. + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -30,13 +30,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -48,7 +45,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -58,7 +56,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -69,7 +66,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -88,13 +84,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -124,7 +117,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -135,7 +127,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -156,13 +147,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -186,7 +174,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -210,7 +197,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/cf04ae54e680c0b28e8311459cb8fd11315485a0.patch b/patches/cf04ae54e680c0b28e8311459cb8fd11315485a0.patch new file mode 100644 index 0000000..2a96087 --- /dev/null +++ b/patches/cf04ae54e680c0b28e8311459cb8fd11315485a0.patch @@ -0,0 +1,2060 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 8bae3da..c6a45f8 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,6 +1,7 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DEFAULT_BUF_SIZE}; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -42,7 +43,6 @@ use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DE + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -66,7 +66,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -87,7 +86,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -117,7 +115,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -140,7 +137,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -168,7 +164,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -191,7 +186,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -215,7 +209,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -233,7 +226,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -253,7 +245,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -309,7 +300,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -329,7 +319,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -342,7 +331,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index fa7bd0d..061c4c9 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,9 +1,9 @@ +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; +-use crate::mem; ++use core::mem; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -65,7 +65,6 @@ use crate::mem; + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -87,7 +86,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -105,7 +103,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -200,7 +197,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -220,7 +216,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -238,7 +233,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -258,7 +252,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -282,7 +275,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -313,7 +305,6 @@ impl BufWriter { + /// assert_eq!(recovered_writer.len(), 0); + /// assert_eq!(&buffered_data.unwrap(), b"ata"); + /// ``` +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_raw_parts(mut self) -> (W, Result, WriterPanicked>) { + let buf = mem::take(&mut self.buf); + let buf = if !self.panicked { Ok(buf) } else { Err(WriterPanicked { buf }) }; +@@ -321,7 +312,6 @@ impl BufWriter { + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + /// Error returned for the buffered data from `BufWriter::into_raw_parts`, when the underlying + /// writer has previously panicked. Contains the (possibly partly written) buffered data. + /// +@@ -355,7 +345,6 @@ pub struct WriterPanicked { + impl WriterPanicked { + /// Returns the perhaps-unwritten data. Some of this data may have been written by the + /// panicking call(s) to the underlying writer, so simply writing it again is not a good idea. +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_inner(self) -> Vec { + self.buf + } +@@ -364,22 +353,12 @@ impl WriterPanicked { + "BufWriter inner writer panicked, what data remains unwritten is not known"; + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] +-impl error::Error for WriterPanicked { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- Self::DESCRIPTION +- } +-} +- +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Display for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + write!(f, "{}", Self::DESCRIPTION) + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Debug for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("WriterPanicked") +@@ -388,7 +367,6 @@ impl fmt::Debug for WriterPanicked { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -485,7 +463,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -498,7 +475,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -509,7 +485,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index d0c859d..a052adf 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index 6549781..0dc7440 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,7 +119,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } +@@ -143,7 +139,6 @@ impl IntoInnerError { + /// let err = into_inner_err.into_error(); + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_error(self) -> Error { + self.1 + } +@@ -167,28 +162,17 @@ impl IntoInnerError { + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// assert_eq!(recovered_writer.buffer(), b"t be actually written"); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_parts(self) -> (Error, W) { + (self.1, self.0) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/copy.rs b/copy.rs +index b88bca2..7593702 100644 +--- a/copy.rs ++++ b/copy.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, ErrorKind, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,19 +39,12 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, + W: Write, + { +- cfg_if::cfg_if! { +- if #[cfg(any(target_os = "linux", target_os = "android"))] { +- crate::sys::kernel_copy::copy_spec(reader, writer) +- } else { +- generic_copy(reader, writer) +- } +- } ++ generic_copy(reader, writer) + } + + /// The general read-write-loop implementation of +diff --git a/cursor.rs b/cursor.rs +index bbee2cc..dc75216 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,8 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,8 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn get_ref(&self) -> &T { + &self.inner + } +@@ -152,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -176,8 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn position(&self) -> u64 { + self.pos + } +@@ -199,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -245,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -274,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -285,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -326,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -354,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -366,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -389,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -410,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -431,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 00bf8b9..5c0e7cd 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -216,7 +222,6 @@ impl BufRead for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -279,6 +284,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -288,7 +294,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -310,7 +316,6 @@ impl BufRead for &[u8] { + /// If the number of bytes to be written exceeds the size of the slice, write operations will + /// return short writes: ultimately, `Ok(0)`; in this situation, `write_all` returns an error of + /// kind `ErrorKind::WriteZero`. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -356,7 +361,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index c87a565..138fcf7 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -246,58 +246,48 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::copy::copy; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[unstable(feature = "internal_output_capture", issue = "none")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::set_output_capture; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + pub(crate) mod copy; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -324,6 +314,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -351,10 +342,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -505,7 +498,6 @@ pub(crate) fn default_read_exact(this: &mut R, mut buf: &mut [ + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -576,7 +568,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -588,7 +579,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -601,7 +591,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -625,7 +614,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -677,7 +665,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -720,7 +708,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -784,7 +772,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, buf: &mut [u8]) -> Result<()> { + default_read_exact(self, buf) + } +@@ -823,7 +810,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -860,7 +846,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -898,7 +883,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -937,7 +921,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -987,29 +970,71 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +-#[unstable(feature = "io_read_to_string", issue = "80218")] ++#[cfg(feature="collections")] + pub fn read_to_string(reader: &mut R) -> Result { + let mut buf = String::new(); + reader.read_to_string(&mut buf)?; + Ok(buf) + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1022,10 +1047,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1060,7 +1084,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1084,7 +1107,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1094,7 +1116,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1107,18 +1128,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1131,10 +1148,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1168,7 +1184,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1192,7 +1207,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1203,13 +1217,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1223,21 +1235,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1291,7 +1300,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1338,7 +1346,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1351,7 +1358,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1366,7 +1372,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1394,7 +1399,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1428,7 +1432,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1490,7 +1493,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1543,7 +1545,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1599,7 +1600,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1634,7 +1634,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1648,7 +1647,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1685,7 +1683,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1723,7 +1720,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1733,29 +1729,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1831,7 +1824,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1872,7 +1865,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1894,7 +1886,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1951,7 +1942,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -2014,7 +2004,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2052,7 +2041,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2089,7 +2077,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2104,7 +2091,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2130,7 +2116,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2153,7 +2138,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2180,20 +2164,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2221,7 +2202,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2246,7 +2227,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2279,7 +2259,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2307,7 +2286,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2332,7 +2310,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2357,7 +2334,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2386,13 +2362,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2410,6 +2384,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2418,7 +2393,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2445,13 +2420,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2475,14 +2448,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2507,13 +2480,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index db84545..8e88c3d 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,14 +3,14 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, Initializer, IoSlice, IoSliceMut, Read, Write}; ++use core::fmt; ++use crate::io::{self, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; + + /// A reader which is always at EOF. + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -30,13 +30,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -48,7 +45,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -58,7 +56,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -69,7 +66,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -88,13 +84,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -124,7 +117,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -135,7 +127,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -156,13 +147,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -186,7 +174,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -210,7 +197,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/d8cc2c1e4f8fa6bd49fe9c395353f9e24c7b51fc.patch b/patches/d8cc2c1e4f8fa6bd49fe9c395353f9e24c7b51fc.patch new file mode 100644 index 0000000..8a5bd4f --- /dev/null +++ b/patches/d8cc2c1e4f8fa6bd49fe9c395353f9e24c7b51fc.patch @@ -0,0 +1,1888 @@ +diff --git a/buffered.rs b/buffered.rs +index 046b1a6..2ad53d6 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -222,7 +215,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -240,7 +232,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -260,7 +251,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -302,7 +292,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -322,7 +311,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -335,7 +323,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -446,7 +433,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -481,7 +467,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -496,7 +481,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -514,7 +498,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -561,7 +544,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -581,7 +563,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -599,7 +580,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -620,7 +600,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -644,7 +623,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -653,7 +631,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -693,7 +670,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -706,7 +682,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -716,7 +691,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -755,7 +729,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -790,28 +763,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -882,7 +844,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -903,7 +864,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -924,7 +884,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -945,7 +904,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -970,7 +928,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -998,7 +955,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -1006,7 +962,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1107,7 +1062,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index f3e3fc8..0e6fcdb 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -272,7 +263,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -283,15 +274,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -324,6 +324,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -352,6 +353,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -364,7 +366,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -387,7 +388,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -408,7 +409,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -429,8 +430,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index d80a388..8991308 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -432,12 +396,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -466,8 +429,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -493,10 +455,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -509,8 +470,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -518,13 +477,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -532,34 +489,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 01dff0b..eb78a0f 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -30,11 +34,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -45,7 +51,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -77,14 +82,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -107,7 +111,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -129,11 +133,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -144,7 +150,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -176,14 +182,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -227,7 +233,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -290,6 +295,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -299,7 +305,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -317,7 +323,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -363,7 +368,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 717d286..8a46366 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -258,54 +258,44 @@ + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + // ignore-tidy-filelength + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::mem; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++use core::mem; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -332,6 +322,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -359,10 +350,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -498,7 +491,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning + /// how many bytes were read. +@@ -570,7 +562,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -582,7 +573,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -595,7 +585,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -622,7 +611,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -675,7 +663,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -718,7 +706,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -781,7 +769,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -835,7 +822,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -877,7 +863,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -915,7 +900,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -954,7 +938,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -963,22 +946,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -991,10 +1016,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1029,7 +1053,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1053,7 +1076,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1063,7 +1085,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1076,18 +1097,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1100,10 +1117,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1137,7 +1153,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1161,7 +1176,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1172,13 +1186,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1192,21 +1204,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1260,7 +1269,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. + /// +@@ -1308,7 +1316,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1319,7 +1326,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1332,7 +1338,6 @@ pub trait Write { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1360,7 +1365,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1395,7 +1399,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1459,7 +1462,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + while !bufs.is_empty() { + match self.write_vectored(bufs) { +@@ -1512,7 +1514,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1568,7 +1569,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1603,7 +1603,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1619,7 +1618,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1657,7 +1655,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1696,7 +1693,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1708,29 +1704,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1809,7 +1802,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1850,7 +1843,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1872,7 +1864,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1932,7 +1923,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1995,7 +1985,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2036,7 +2025,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2078,7 +2066,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2093,7 +2080,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2119,7 +2105,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2142,7 +2127,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2169,20 +2153,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2210,7 +2191,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2235,7 +2216,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2270,7 +2250,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2298,7 +2277,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2323,7 +2301,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2348,7 +2325,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2377,13 +2353,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2401,6 +2375,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2409,7 +2384,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2436,13 +2411,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2466,14 +2439,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2498,13 +2471,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b9d5dc2..07d090e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -190,7 +184,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -203,7 +196,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -222,12 +214,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -251,7 +241,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/d9cd4a33f53689bc0847775669a14f666a138fd7.patch b/patches/d9cd4a33f53689bc0847775669a14f666a138fd7.patch new file mode 100644 index 0000000..1bee0af --- /dev/null +++ b/patches/d9cd4a33f53689bc0847775669a14f666a138fd7.patch @@ -0,0 +1,1903 @@ +diff --git a/buffered.rs b/buffered.rs +index 5ad8f81..8313e78 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -3,15 +3,15 @@ + #[cfg(test)] + mod tests; + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -52,7 +52,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -76,7 +75,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -97,7 +95,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -127,7 +124,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -150,7 +146,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -178,7 +173,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -201,7 +195,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -225,7 +218,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -243,7 +235,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -263,7 +254,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -305,7 +295,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -325,7 +314,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -338,7 +326,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -447,7 +434,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: Write::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: Write::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -482,7 +468,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -497,7 +482,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -515,7 +499,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -610,7 +593,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -630,7 +612,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -648,7 +629,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -668,7 +648,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -692,7 +671,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -701,7 +679,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -765,7 +742,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -778,7 +754,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -789,7 +764,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -829,7 +803,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -864,28 +837,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -1222,7 +1184,6 @@ impl<'a, W: Write> Write for LineWriterShim<'a, W> { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -1242,7 +1203,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -1263,7 +1223,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -1284,7 +1243,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -1309,7 +1267,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -1337,7 +1294,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner + .into_inner() +@@ -1345,7 +1301,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -1376,7 +1331,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index 5733735..0fdd84a 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,7 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -111,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -129,7 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -150,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -196,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -242,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -271,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -282,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -323,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -351,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -363,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -386,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -407,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -428,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index e09e7ba..126a710 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -230,7 +236,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -293,6 +298,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -302,7 +308,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -320,7 +326,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -366,7 +371,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index adea8a8..e647c6b 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -247,56 +247,46 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -323,6 +313,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -350,10 +341,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -487,7 +480,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -558,7 +550,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -570,7 +561,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -583,7 +573,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -607,7 +596,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -659,7 +647,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -702,7 +690,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -766,7 +754,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -820,7 +807,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -857,7 +843,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -895,7 +880,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -934,7 +918,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -943,22 +926,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -971,10 +996,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1009,7 +1033,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1033,7 +1056,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1043,7 +1065,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1056,18 +1077,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1080,10 +1097,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1117,7 +1133,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1141,7 +1156,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1152,13 +1166,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1172,21 +1184,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1240,7 +1249,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1287,7 +1295,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1300,7 +1307,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1315,7 +1321,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1343,7 +1348,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1377,7 +1381,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1439,7 +1442,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1492,7 +1494,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1548,7 +1549,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1583,7 +1583,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1597,7 +1596,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1634,7 +1632,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1672,7 +1669,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1682,29 +1678,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1780,7 +1773,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1821,7 +1814,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1843,7 +1835,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1900,7 +1891,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1963,7 +1953,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2002,7 +1991,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2039,7 +2027,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2054,7 +2041,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2080,7 +2066,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2103,7 +2088,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2130,20 +2114,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2171,7 +2152,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2196,7 +2177,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2229,7 +2209,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2257,7 +2236,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2282,7 +2260,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2307,7 +2284,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2336,13 +2312,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2360,6 +2334,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2368,7 +2343,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2395,13 +2370,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2425,14 +2398,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2457,13 +2430,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b3df6f4..158ae40 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,9 +3,10 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -45,7 +46,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -78,7 +78,6 @@ where + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -98,12 +97,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -115,7 +112,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -125,7 +123,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -190,7 +184,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -201,7 +194,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -222,12 +214,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -251,7 +241,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/dad56c39474377c7d47e261b380d0be3aed104cc.patch b/patches/dad56c39474377c7d47e261b380d0be3aed104cc.patch new file mode 100644 index 0000000..b7759d8 --- /dev/null +++ b/patches/dad56c39474377c7d47e261b380d0be3aed104cc.patch @@ -0,0 +1,1797 @@ +diff --git a/buffered.rs b/buffered.rs +index aaf628e..259eba3 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,13 +1,13 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, Initializer, DEFAULT_BUF_SIZE, Error, ErrorKind, SeekFrom, IoSlice, + IoSliceMut}; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -47,7 +47,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -71,7 +70,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -92,7 +90,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -127,7 +124,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { &self.inner } + + /// Gets a mutable reference to the underlying reader. +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { &mut self.inner } + + /// Returns a reference to the internally buffered data. +@@ -172,7 +167,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -195,7 +189,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { self.inner } + + /// Invalidates all data in the internal buffer. +@@ -211,7 +204,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -231,7 +223,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -269,7 +260,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -289,7 +279,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader where R: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufReader") +@@ -299,7 +288,6 @@ impl fmt::Debug for BufReader where R: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -408,7 +396,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -443,7 +430,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -458,7 +444,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -476,7 +461,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { + inner: Some(inner), +@@ -525,7 +509,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.as_ref().unwrap() } + + /// Gets a mutable reference to the underlying writer. +@@ -543,7 +526,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.as_mut().unwrap() } + + /// Returns a reference to the internally buffered data. +@@ -559,7 +541,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -583,7 +564,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -592,7 +572,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -628,7 +607,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufWriter") +@@ -638,7 +616,6 @@ impl fmt::Debug for BufWriter where W: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -648,7 +625,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -687,7 +663,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { &self.1 } + + /// Returns the buffered writer instance which generated the error. +@@ -720,23 +695,13 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { self.0 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { iie.1 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -807,7 +772,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -828,7 +792,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -849,7 +812,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { + inner: BufWriter::with_capacity(capacity, inner), +@@ -873,7 +835,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.get_ref() } + + /// Gets a mutable reference to the underlying writer. +@@ -896,7 +857,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.get_mut() } + + /// Unwraps this `LineWriter`, returning the underlying writer. +@@ -922,7 +882,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { +@@ -933,7 +892,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -978,7 +936,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("LineWriter") +diff --git a/cursor.rs b/cursor.rs +index a94176e..7768d39 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Initializer, SeekFrom, Error, ErrorKind, IoSlice, IoSliceMut}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { self.inner } + + /// Gets a reference to the underlying value in this cursor. +@@ -128,7 +125,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { &self.inner } + + /// Gets a mutable reference to the underlying value in this cursor. +@@ -147,7 +143,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { &mut self.inner } + + /// Returns the current position of this cursor. +@@ -169,7 +164,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { self.pos } + + /// Sets the position of this cursor. +@@ -189,11 +183,9 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { self.pos = pos; } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor where T: AsRef<[u8]> { + fn seek(&mut self, style: SeekFrom) -> io::Result { + let (base_pos, offset) = match style { +@@ -222,10 +214,9 @@ impl io::Seek for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor where T: AsRef<[u8]> { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -244,7 +235,7 @@ impl Read for Cursor where T: AsRef<[u8]> { + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -255,12 +246,16 @@ impl Read for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor where T: AsRef<[u8]> { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++impl Cursor where T: AsRef<[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor where T: AsRef<[u8]> { ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { self.get_buf() } + fn consume(&mut self, amt: usize) { self.pos += amt as u64; } + } + +@@ -292,6 +287,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new(ErrorKind::InvalidInput, +@@ -318,6 +314,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -331,7 +328,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -347,7 +343,7 @@ impl Write for Cursor<&mut [u8]> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -361,7 +357,7 @@ impl Write for Cursor<&mut Vec> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -375,8 +371,8 @@ impl Write for Cursor> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index c29a68e..c94d8c5 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,13 @@ +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; +-use crate::convert::From; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++use core::convert::Into; ++use core::fmt; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++use core::result; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; ++use core::convert::From; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +43,6 @@ use crate::convert::From; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +56,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +69,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +90,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +130,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +142,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +156,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +186,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -245,14 +230,13 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error +- where E: Into> ++ where E: Into + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { + repr: Repr::Custom(Box::new(Custom { + kind, +@@ -261,24 +245,6 @@ impl Error { + } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -304,7 +270,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -335,7 +300,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -369,12 +333,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error+Send+Sync+'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -440,12 +403,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error+Send+Sync+'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -474,8 +436,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -501,10 +462,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -516,22 +476,18 @@ impl fmt::Debug for Repr { + match *self { + Repr::Os(code) => + fmt.debug_struct("Os") +- .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)).finish(), ++ .field("code", &code).finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), + } + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -539,33 +495,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index c959f2d..b645bc8 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,13 +1,15 @@ +-use crate::cmp; +-use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, BufRead, Error, ErrorKind, +- IoSliceMut, IoSlice}; +-use crate::fmt; +-use crate::mem; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++use core::cmp; ++use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, Error, ErrorKind, IoSliceMut, IoSlice}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::fmt; ++use core::mem; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -24,11 +26,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -39,7 +43,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -62,12 +65,11 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -86,7 +88,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -103,11 +105,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -118,7 +122,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -141,12 +145,12 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -186,7 +190,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -245,6 +248,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -254,7 +258,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(*self) } +@@ -268,7 +272,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -307,7 +310,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index f2b6ce6..1d04b7c 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,50 +257,38 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::slice; +-use crate::str; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(feature="collections")] use collections::string::String; ++use core::str; ++#[cfg(feature="collections")] use collections::vec::Vec; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::slice; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++ ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Result, Error, ErrorKind}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, sink, Sink, empty, Empty, repeat, Repeat}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stdin, stdout, stderr, Stdin, Stdout, Stderr}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StdoutLock, StderrLock, StdinLock}; +-#[unstable(feature = "print_internals", issue = "0")] +-pub use self::stdio::{_print, _eprint}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; + + pub mod prelude; +-mod buffered; ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + mod util; +-mod stdio; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { buf: &'a mut Vec, len: usize } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { self.buf.set_len(self.len); } +@@ -325,6 +313,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where F: FnOnce(&mut Vec) -> Result + { +@@ -352,10 +341,12 @@ fn append_to_string(buf: &mut String, f: F) -> Result + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation(r: &mut R, + buf: &mut Vec, + reservation_size: usize) -> Result +@@ -484,7 +475,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -552,7 +542,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -563,7 +552,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -590,7 +578,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -643,7 +630,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -686,7 +673,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -749,7 +736,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -801,7 +787,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + + /// Transforms this `Read` instance to an [`Iterator`] over its bytes. +@@ -838,7 +823,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes where Self: Sized { + Bytes { inner: self } + } +@@ -873,7 +857,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain where Self: Sized { + Chain { first: self, second: next, done_first: false } + } +@@ -909,22 +892,64 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take where Self: Sized { + Take { inner: self, limit: limit } + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -937,10 +962,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -976,7 +1000,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1000,7 +1023,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1010,7 +1032,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1023,11 +1044,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1040,10 +1059,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1078,7 +1096,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(mem::replace(&mut bufs, &mut []), 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1102,7 +1119,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1113,13 +1129,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1133,21 +1147,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1201,7 +1212,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1250,7 +1260,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1261,7 +1270,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1289,7 +1297,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1322,7 +1329,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1374,7 +1380,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1430,7 +1435,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + } + +@@ -1460,7 +1464,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1476,7 +1479,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1514,7 +1516,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1553,7 +1554,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1565,29 +1565,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + -> Result { + let mut read = 0; +@@ -1667,7 +1664,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1708,7 +1705,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1730,7 +1726,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1786,7 +1781,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1845,7 +1839,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1886,7 +1879,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split where Self: Sized { + Split { buf: self, delim: byte } + } +@@ -1925,7 +1917,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines where Self: Sized { + Lines { buf: self } + } +@@ -1937,7 +1928,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -1963,7 +1953,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -1986,7 +1975,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2013,13 +2001,11 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain") +@@ -2029,7 +2015,6 @@ impl fmt::Debug for Chain { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2061,7 +2046,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2088,7 +2073,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2123,7 +2107,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { self.limit } + + /// Sets the number of bytes that can be read before this instance will +@@ -2149,7 +2132,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2174,7 +2156,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2199,7 +2180,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2228,13 +2208,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2252,6 +2230,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + let reservation_size = cmp::min(self.limit, 32) as usize; + +@@ -2259,7 +2238,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2286,13 +2265,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2316,14 +2293,14 @@ impl Iterator for Bytes { + /// `BufRead`. Please see the documentation of `split()` for more details. + /// + /// [split]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2348,13 +2325,13 @@ impl Iterator for Split { + /// `BufRead`. Please see the documentation of `lines()` for more details. + /// + /// [lines]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 2e19edf..66294a3 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Write, Seek}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{Read, Write, BufRead, Seek}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index 33cc87e..75b8032 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, Read, Initializer, Write, ErrorKind, BufRead, IoSlice, IoSliceMut}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, Read, Initializer, Write, ErrorKind, IoSlice, IoSliceMut}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where R: Read, W: Write + { +@@ -70,7 +70,6 @@ pub fn copy(reader: &mut R, writer: &mut W) -> io::Result< + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { _priv: () } + + /// Constructs a new handle to an empty reader. +@@ -90,10 +89,8 @@ pub struct Empty { _priv: () } + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { Empty { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { Ok(0) } +@@ -103,7 +100,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(&[]) } +@@ -111,7 +109,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -124,7 +121,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { byte: u8 } + + /// Creates an instance of a reader that infinitely repeats one byte. +@@ -141,10 +137,8 @@ pub struct Repeat { byte: u8 } + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { Repeat { byte } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -169,7 +163,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -182,7 +175,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { _priv: () } + + /// Creates an instance of a writer which will successfully consume all data. +@@ -199,10 +191,8 @@ pub struct Sink { _priv: () } + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { Sink { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { Ok(buf.len()) } +@@ -217,7 +207,6 @@ impl Write for Sink { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/dad8e11e9fcbd76c0a2dc47211dcd654effed010.patch b/patches/dad8e11e9fcbd76c0a2dc47211dcd654effed010.patch new file mode 100644 index 0000000..9f404a6 --- /dev/null +++ b/patches/dad8e11e9fcbd76c0a2dc47211dcd654effed010.patch @@ -0,0 +1,1891 @@ +diff --git a/buffered.rs b/buffered.rs +index f3aadf2..3826382 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -49,7 +49,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -73,7 +72,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -94,7 +92,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -124,7 +121,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -147,7 +143,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -222,7 +215,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -240,7 +232,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -260,7 +251,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -302,7 +292,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -322,7 +311,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -335,7 +323,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -444,7 +431,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: Write::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: Write::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -479,7 +465,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -494,7 +479,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -512,7 +496,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -559,7 +542,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -579,7 +561,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -597,7 +578,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -617,7 +597,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -641,7 +620,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -650,7 +628,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -690,7 +667,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -703,7 +679,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -713,7 +688,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -753,7 +727,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -788,28 +761,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -878,7 +840,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -899,7 +860,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -920,7 +880,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -941,7 +900,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -966,7 +924,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -994,7 +951,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -1002,7 +958,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1103,7 +1058,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index 58343f6..6750136 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -67,7 +67,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -90,7 +89,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -108,7 +106,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -126,7 +123,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -147,7 +143,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -171,7 +166,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -193,13 +187,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -239,13 +231,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -268,7 +259,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -279,15 +270,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -320,6 +320,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -348,6 +349,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -360,7 +362,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -383,7 +384,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -404,7 +405,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -425,8 +426,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index e6eda2c..be46887 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -51,12 +56,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -66,13 +69,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -84,48 +90,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -137,10 +130,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -151,12 +142,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -164,7 +153,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -173,7 +161,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -204,7 +191,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -244,36 +230,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -299,7 +266,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -333,7 +299,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -369,12 +334,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -440,12 +404,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -476,8 +439,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -503,10 +465,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -519,8 +480,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -528,13 +487,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -542,34 +499,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 01dff0b..eb78a0f 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -30,11 +34,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -45,7 +51,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -77,14 +82,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -107,7 +111,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -129,11 +133,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -144,7 +150,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -176,14 +182,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -227,7 +233,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -290,6 +295,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -299,7 +305,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -317,7 +323,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -363,7 +368,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 3245629..7be5680 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -247,53 +247,43 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -320,6 +310,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -347,10 +338,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -484,7 +477,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -555,7 +547,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -567,7 +558,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -580,7 +570,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -604,7 +593,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -656,7 +644,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -699,7 +687,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -763,7 +751,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -817,7 +804,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -854,7 +840,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -892,7 +877,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -931,7 +915,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -940,22 +923,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -968,10 +993,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1006,7 +1030,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1030,7 +1053,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1040,7 +1062,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1053,18 +1074,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1077,10 +1094,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1114,7 +1130,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1138,7 +1153,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1149,13 +1163,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1169,21 +1181,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1237,7 +1246,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1284,7 +1292,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1297,7 +1304,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1312,7 +1318,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1340,7 +1345,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1374,7 +1378,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1436,7 +1439,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1489,7 +1491,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1545,7 +1546,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1580,7 +1580,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1594,7 +1593,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1631,7 +1629,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1669,7 +1666,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1679,29 +1675,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1777,7 +1770,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1818,7 +1811,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1840,7 +1832,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1897,7 +1888,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1960,7 +1950,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1999,7 +1988,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2036,7 +2024,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2051,7 +2038,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2077,7 +2063,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2100,7 +2085,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2127,20 +2111,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2168,7 +2149,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2193,7 +2174,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2226,7 +2206,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2254,7 +2233,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2279,7 +2257,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2304,7 +2281,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2333,13 +2309,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2357,6 +2331,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2365,7 +2340,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2392,13 +2367,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2422,14 +2395,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2454,13 +2427,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index a093b74..1e468ae 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -42,7 +43,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -75,7 +75,6 @@ where + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -95,12 +94,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -112,7 +109,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -122,7 +120,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -133,7 +130,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -152,12 +148,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -187,7 +181,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -219,12 +211,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -248,7 +238,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/db4a97c4cbcb160b3754c803284dd0110d1de1e4.patch b/patches/db4a97c4cbcb160b3754c803284dd0110d1de1e4.patch new file mode 100644 index 0000000..fe2473e --- /dev/null +++ b/patches/db4a97c4cbcb160b3754c803284dd0110d1de1e4.patch @@ -0,0 +1,2084 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 02b0fc0..fe6e4af 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,8 +1,9 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, SizeHint, DEFAULT_BUF_SIZE, + }; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -44,7 +45,6 @@ use crate::io::{ + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -68,7 +68,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -89,7 +88,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buf = Box::new_uninit_slice(capacity).assume_init(); +@@ -118,7 +116,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -141,7 +138,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -169,7 +165,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -192,7 +187,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -216,7 +210,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -234,7 +227,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -254,7 +246,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -310,7 +301,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -330,7 +320,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -343,7 +332,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index 65bc2fc..46cd6b8 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,9 +1,9 @@ +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; +-use crate::mem; ++use core::mem; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -65,7 +65,6 @@ use crate::mem; + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -87,7 +86,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -105,7 +103,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -200,7 +197,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -220,7 +216,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -238,7 +233,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -270,7 +264,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -294,7 +287,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -325,7 +317,6 @@ impl BufWriter { + /// assert_eq!(recovered_writer.len(), 0); + /// assert_eq!(&buffered_data.unwrap(), b"ata"); + /// ``` +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_raw_parts(mut self) -> (W, Result, WriterPanicked>) { + let buf = mem::take(&mut self.buf); + let buf = if !self.panicked { Ok(buf) } else { Err(WriterPanicked { buf }) }; +@@ -333,7 +324,6 @@ impl BufWriter { + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + /// Error returned for the buffered data from `BufWriter::into_raw_parts`, when the underlying + /// writer has previously panicked. Contains the (possibly partly written) buffered data. + /// +@@ -367,7 +357,6 @@ pub struct WriterPanicked { + impl WriterPanicked { + /// Returns the perhaps-unwritten data. Some of this data may have been written by the + /// panicking call(s) to the underlying writer, so simply writing it again is not a good idea. +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_inner(self) -> Vec { + self.buf + } +@@ -376,22 +365,12 @@ impl WriterPanicked { + "BufWriter inner writer panicked, what data remains unwritten is not known"; + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] +-impl error::Error for WriterPanicked { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- Self::DESCRIPTION +- } +-} +- +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Display for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + write!(f, "{}", Self::DESCRIPTION) + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Debug for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("WriterPanicked") +@@ -400,7 +379,6 @@ impl fmt::Debug for WriterPanicked { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -497,7 +475,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -510,7 +487,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -521,7 +497,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index d0c859d..a052adf 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index 6549781..0dc7440 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,7 +119,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } +@@ -143,7 +139,6 @@ impl IntoInnerError { + /// let err = into_inner_err.into_error(); + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_error(self) -> Error { + self.1 + } +@@ -167,28 +162,17 @@ impl IntoInnerError { + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// assert_eq!(recovered_writer.buffer(), b"t be actually written"); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_parts(self) -> (Error, W) { + (self.1, self.0) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/copy.rs b/copy.rs +index eb60df2..df99a47 100644 +--- a/copy.rs ++++ b/copy.rs +@@ -1,5 +1,6 @@ +-use super::{BufWriter, ErrorKind, Read, Result, Write, DEFAULT_BUF_SIZE}; +-use crate::mem::MaybeUninit; ++use super::{ErrorKind, Read, Result, Write, DEFAULT_BUF_SIZE}; ++#[cfg(feature = "collections")] use super::BufWriter; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,19 +40,12 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> Result + where + R: Read, + W: Write, + { +- cfg_if::cfg_if! { +- if #[cfg(any(target_os = "linux", target_os = "android"))] { +- crate::sys::kernel_copy::copy_spec(reader, writer) +- } else { +- generic_copy(reader, writer) +- } +- } ++ generic_copy(reader, writer) + } + + /// The userspace read-write-loop implementation of `io::copy` that is used when +@@ -76,6 +70,7 @@ impl BufferedCopySpec for W { + } + } + ++#[cfg(feature = "collections")] + impl BufferedCopySpec for BufWriter { + fn copy_to(reader: &mut R, writer: &mut Self) -> Result { + if writer.capacity() < DEFAULT_BUF_SIZE { +diff --git a/cursor.rs b/cursor.rs +index bbee2cc..dc75216 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,8 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,8 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn get_ref(&self) -> &T { + &self.inner + } +@@ -152,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -176,8 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn position(&self) -> u64 { + self.pos + } +@@ -199,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -245,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -274,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -285,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -326,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -354,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -366,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -389,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -410,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -431,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 9870cfc..df98b8e 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,18 +1,22 @@ + #[cfg(test)] + mod tests; + +-use crate::alloc::Allocator; +-use crate::cmp; +-use crate::fmt; ++#[cfg(feature="collections")] use core::alloc::Allocator; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -34,11 +38,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -49,7 +55,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -81,14 +86,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -111,7 +115,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -133,11 +137,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -148,7 +154,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -180,14 +186,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -217,7 +223,6 @@ impl BufRead for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -280,6 +285,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -289,7 +295,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -311,7 +317,6 @@ impl BufRead for &[u8] { + /// If the number of bytes to be written exceeds the size of the slice, write operations will + /// return short writes: ultimately, `Ok(0)`; in this situation, `write_all` returns an error of + /// kind `ErrorKind::WriteZero`. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -357,7 +362,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 6abb300..ef02bec 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -246,58 +246,48 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::copy::copy; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[unstable(feature = "internal_output_capture", issue = "none")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::set_output_capture; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + pub(crate) mod copy; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -324,6 +314,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -351,10 +342,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -504,7 +497,6 @@ pub(crate) fn default_read_exact(this: &mut R, mut buf: &mut [ + /// [`&str`]: prim@str + /// [`std::io`]: self + /// [`File`]: crate::fs::File +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -580,7 +572,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -592,7 +583,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -605,7 +595,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -629,7 +618,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -681,7 +669,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -724,7 +712,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -788,7 +776,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, buf: &mut [u8]) -> Result<()> { + default_read_exact(self, buf) + } +@@ -827,7 +814,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -864,7 +850,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -902,7 +887,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -941,7 +925,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -991,29 +974,71 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +-#[unstable(feature = "io_read_to_string", issue = "80218")] ++#[cfg(feature="collections")] + pub fn read_to_string(reader: &mut R) -> Result { + let mut buf = String::new(); + reader.read_to_string(&mut buf)?; + Ok(buf) + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1026,10 +1051,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1064,7 +1088,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1088,7 +1111,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1098,7 +1120,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1111,18 +1132,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1135,10 +1152,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1172,7 +1188,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1196,7 +1211,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1207,13 +1221,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1227,21 +1239,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1295,7 +1304,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1342,7 +1350,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1355,7 +1362,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1370,7 +1376,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1398,7 +1403,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1432,7 +1436,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1494,7 +1497,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1547,7 +1549,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1603,7 +1604,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1638,7 +1638,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1652,7 +1651,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1689,7 +1687,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_stream_len", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1726,7 +1723,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "seek_convenience", since = "1.51.0")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1736,29 +1732,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1834,7 +1827,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1875,7 +1868,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1897,7 +1889,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1954,7 +1945,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -2017,7 +2007,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2055,7 +2044,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2092,7 +2080,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2107,7 +2094,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2133,7 +2119,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2156,7 +2141,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2183,20 +2167,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2224,7 +2205,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2262,7 +2243,6 @@ impl SizeHint for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2295,7 +2275,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2323,7 +2302,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2348,7 +2326,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2373,7 +2350,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2402,13 +2378,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2426,6 +2400,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2434,7 +2409,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2461,13 +2436,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2515,14 +2488,14 @@ impl SizeHint for T { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2547,13 +2520,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index d806431..6b9791a 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index f472361..0a1899d 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,16 +3,16 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; ++use core::fmt; + use crate::io::{ +- self, BufRead, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, SizeHint, Write, ++ self, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, SizeHint, Write, + }; ++#[cfg(feature="collections")] use crate::io::BufRead; + + /// A reader which is always at EOF. + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -32,13 +32,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -50,7 +47,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -60,7 +58,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "empty_seek", since = "1.51.0")] + impl Seek for Empty { + fn seek(&mut self, _pos: SeekFrom) -> io::Result { + Ok(0) +@@ -75,7 +72,6 @@ impl Seek for Empty { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -92,7 +88,6 @@ impl SizeHint for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -111,13 +106,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -147,7 +139,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -158,7 +149,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -179,13 +169,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -209,7 +196,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -233,7 +219,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/dd8f07223346b06da723c25a3ac42f874e6c945c.patch b/patches/dd8f07223346b06da723c25a3ac42f874e6c945c.patch new file mode 100644 index 0000000..21223f6 --- /dev/null +++ b/patches/dd8f07223346b06da723c25a3ac42f874e6c945c.patch @@ -0,0 +1,1832 @@ +diff --git a/buffered.rs b/buffered.rs +index 9e6849b..7021de4 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -216,7 +209,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -236,7 +228,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -274,7 +265,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -294,7 +284,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -307,7 +296,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -418,7 +406,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -453,7 +440,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -468,7 +454,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -486,7 +471,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -533,7 +517,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -553,7 +536,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -571,7 +553,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -595,7 +576,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -604,7 +584,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -640,7 +619,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -653,7 +631,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -663,7 +640,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -702,7 +678,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -737,28 +712,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -829,7 +793,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -850,7 +813,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -871,7 +833,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -892,7 +853,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -917,7 +877,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -945,7 +904,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -953,7 +911,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1059,7 +1016,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index 9787cbb..1cf83d3 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -268,7 +259,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -279,15 +270,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -320,6 +320,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -348,6 +349,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -360,7 +362,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -378,7 +379,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -394,7 +395,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -410,8 +411,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index 3b55d9b..c754d1f 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -432,12 +396,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -466,8 +429,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -493,10 +455,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -509,8 +470,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -518,13 +477,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -532,34 +489,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index b7f82e6..c857f83 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -25,11 +29,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -40,7 +46,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -67,14 +72,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -97,7 +101,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -114,11 +118,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -129,7 +135,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -156,14 +162,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -207,7 +213,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -265,6 +270,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -274,7 +280,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -292,7 +298,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -333,7 +338,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 95c8934..b29907e 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,53 +257,43 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -330,6 +320,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -357,10 +348,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -496,7 +489,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -564,7 +556,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -575,7 +566,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -602,7 +592,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -655,7 +644,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -698,7 +687,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -761,7 +750,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -815,7 +803,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -857,7 +844,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -895,7 +881,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -934,7 +919,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -943,16 +927,59 @@ pub trait Read { + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -965,10 +992,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1003,7 +1029,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1027,7 +1052,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1037,7 +1061,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1050,11 +1073,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1067,10 +1088,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1104,7 +1124,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1128,7 +1147,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1139,13 +1157,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1159,21 +1175,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1227,7 +1240,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1276,7 +1288,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1287,7 +1298,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1315,7 +1325,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1348,7 +1357,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1401,7 +1409,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1457,7 +1464,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1492,7 +1498,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1508,7 +1513,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1546,7 +1550,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1585,7 +1588,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1597,29 +1599,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1698,7 +1697,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1739,7 +1738,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1761,7 +1759,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1817,7 +1814,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1876,7 +1872,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1917,7 +1912,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -1959,7 +1953,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -1974,7 +1967,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2000,7 +1992,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2023,7 +2014,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2050,20 +2040,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2091,7 +2078,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2116,7 +2103,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2151,7 +2137,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2179,7 +2164,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2204,7 +2188,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2229,7 +2212,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2258,13 +2240,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2282,6 +2262,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2290,7 +2271,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2317,13 +2298,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2347,14 +2326,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2379,13 +2358,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b09161b..e52119e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -185,7 +179,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -217,12 +209,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -241,7 +231,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/de597fca40d129435c53a69c6662d7bfac29771d.patch b/patches/de597fca40d129435c53a69c6662d7bfac29771d.patch new file mode 100644 index 0000000..efa02cc --- /dev/null +++ b/patches/de597fca40d129435c53a69c6662d7bfac29771d.patch @@ -0,0 +1,1910 @@ +diff --git a/buffered.rs b/buffered.rs +index 97c4b87..ae26453 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -3,15 +3,15 @@ + #[cfg(test)] + mod tests; + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -52,7 +52,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -76,7 +75,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -97,7 +95,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -127,7 +124,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -150,7 +146,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -178,7 +173,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -201,7 +195,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -225,7 +218,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -243,7 +235,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -263,7 +254,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -305,7 +295,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -325,7 +314,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -338,7 +326,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -492,7 +479,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: Write::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: Write::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -527,7 +513,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -542,7 +527,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -560,7 +544,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -655,7 +638,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -675,7 +657,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -693,7 +674,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -713,7 +693,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -737,7 +716,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -746,7 +724,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -810,7 +787,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -823,7 +799,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -834,7 +809,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -874,7 +848,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -909,28 +882,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -1267,7 +1229,6 @@ impl<'a, W: Write> Write for LineWriterShim<'a, W> { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -1287,7 +1248,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -1308,7 +1268,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -1329,7 +1288,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -1354,7 +1312,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -1382,7 +1339,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner + .into_inner() +@@ -1390,7 +1346,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -1421,7 +1376,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index 5733735..0fdd84a 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,7 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -111,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -129,7 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -150,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -196,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -242,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -271,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -282,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -323,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -351,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -363,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -386,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -407,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -428,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index e09e7ba..126a710 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -230,7 +236,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -293,6 +298,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -302,7 +308,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -320,7 +326,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -366,7 +371,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index d9d0380..e647c6b 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -247,55 +247,46 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -322,6 +313,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -349,10 +341,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -486,7 +480,6 @@ where + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -557,7 +550,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -569,7 +561,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -582,7 +573,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -606,7 +596,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -658,7 +647,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -701,7 +690,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -765,7 +754,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -819,7 +807,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -856,7 +843,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -894,7 +880,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -933,7 +918,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -942,22 +926,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -970,10 +996,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1008,7 +1033,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1032,7 +1056,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1042,7 +1065,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1055,18 +1077,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1079,10 +1097,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1116,7 +1133,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1140,7 +1156,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1151,13 +1166,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1171,21 +1184,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1239,7 +1249,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1286,7 +1295,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1299,7 +1307,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1314,7 +1321,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1342,7 +1348,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1376,7 +1381,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1438,7 +1442,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1491,7 +1494,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1547,7 +1549,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1582,7 +1583,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1596,7 +1596,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1633,7 +1632,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1671,7 +1669,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1681,29 +1678,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1779,7 +1773,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1820,7 +1814,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1842,7 +1835,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1899,7 +1891,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1962,7 +1953,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2001,7 +1991,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2038,7 +2027,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2053,7 +2041,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2079,7 +2066,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2102,7 +2088,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2129,20 +2114,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2170,7 +2152,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2195,7 +2177,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2228,7 +2209,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2256,7 +2236,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2281,7 +2260,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2306,7 +2284,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2335,13 +2312,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2359,6 +2334,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2367,7 +2343,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2394,13 +2370,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2424,14 +2398,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2456,13 +2430,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index dc05b96..aa7ee35 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,9 +3,10 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -45,7 +46,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -81,7 +81,6 @@ where + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -101,12 +100,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -118,7 +115,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -128,7 +126,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -139,7 +136,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -158,12 +154,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -193,7 +187,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -204,7 +197,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -225,12 +217,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -254,7 +244,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -278,7 +267,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/df7d9f383848dcb31a2f94bb1df5270ea21aff4b.patch b/patches/df7d9f383848dcb31a2f94bb1df5270ea21aff4b.patch new file mode 100644 index 0000000..8b69c4b --- /dev/null +++ b/patches/df7d9f383848dcb31a2f94bb1df5270ea21aff4b.patch @@ -0,0 +1,1848 @@ +diff --git a/buffered.rs b/buffered.rs +index 8862226..7898006 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -222,7 +215,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -240,7 +232,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -260,7 +251,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -298,7 +288,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -318,7 +307,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -331,7 +319,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -442,7 +429,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -477,7 +463,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -492,7 +477,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -510,7 +494,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -557,7 +540,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -577,7 +559,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -595,7 +576,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -616,7 +596,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -640,7 +619,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -649,7 +627,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -685,7 +662,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -698,7 +674,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -708,7 +683,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -747,7 +721,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -782,28 +755,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -874,7 +836,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -895,7 +856,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -916,7 +876,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -937,7 +896,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -962,7 +920,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -990,7 +947,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -998,7 +954,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1104,7 +1059,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index 9787cbb..1cf83d3 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -268,7 +259,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -279,15 +270,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -320,6 +320,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -348,6 +349,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -360,7 +362,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -378,7 +379,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -394,7 +395,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -410,8 +411,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index 3b55d9b..c754d1f 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -432,12 +396,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -466,8 +429,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -493,10 +455,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -509,8 +470,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -518,13 +477,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -532,34 +489,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index b7f82e6..c857f83 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -25,11 +29,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -40,7 +46,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -67,14 +72,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -97,7 +101,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -114,11 +118,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -129,7 +135,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -156,14 +162,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -207,7 +213,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -265,6 +270,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -274,7 +280,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -292,7 +298,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -333,7 +338,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 67b382c..f8ccb5e 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,53 +257,43 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -330,6 +320,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -357,10 +348,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -496,7 +489,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -564,7 +556,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -575,7 +566,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -602,7 +592,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -655,7 +644,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -698,7 +687,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -761,7 +750,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -815,7 +803,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -857,7 +844,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -895,7 +881,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -934,7 +919,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -943,16 +927,59 @@ pub trait Read { + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -965,10 +992,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1003,7 +1029,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1027,7 +1052,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1037,7 +1061,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1050,11 +1073,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1067,10 +1088,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1104,7 +1124,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1128,7 +1147,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1139,13 +1157,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1159,21 +1175,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1227,7 +1240,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1276,7 +1288,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1287,7 +1298,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1315,7 +1325,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1350,7 +1359,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1403,7 +1411,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1459,7 +1466,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1494,7 +1500,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1510,7 +1515,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1548,7 +1552,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1587,7 +1590,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1599,29 +1601,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1700,7 +1699,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1741,7 +1740,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1763,7 +1761,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1819,7 +1816,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1878,7 +1874,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1919,7 +1914,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -1961,7 +1955,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -1976,7 +1969,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2002,7 +1994,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2025,7 +2016,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2052,20 +2042,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2093,7 +2080,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2118,7 +2105,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2153,7 +2139,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2181,7 +2166,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2206,7 +2190,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2231,7 +2214,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2260,13 +2242,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2284,6 +2264,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2292,7 +2273,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2319,13 +2300,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2349,14 +2328,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2381,13 +2360,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b09161b..e52119e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -185,7 +179,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -217,12 +209,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -241,7 +231,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/e697ffbbcb41559c8de3ca3b94f3b9467e662a19.patch b/patches/e697ffbbcb41559c8de3ca3b94f3b9467e662a19.patch new file mode 100644 index 0000000..f47813c --- /dev/null +++ b/patches/e697ffbbcb41559c8de3ca3b94f3b9467e662a19.patch @@ -0,0 +1,1797 @@ +diff --git a/buffered.rs b/buffered.rs +index 9593a1b..0b6c3eb 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,13 +1,13 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, Initializer, DEFAULT_BUF_SIZE, Error, ErrorKind, SeekFrom, IoSlice, + IoSliceMut}; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -47,7 +47,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -71,7 +70,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -92,7 +90,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -127,7 +124,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { &self.inner } + + /// Gets a mutable reference to the underlying reader. +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { &mut self.inner } + + /// Returns a reference to the internally buffered data. +@@ -172,7 +167,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -195,7 +189,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { self.inner } + + /// Invalidates all data in the internal buffer. +@@ -211,7 +204,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -231,7 +223,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -269,7 +260,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -289,7 +279,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader where R: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufReader") +@@ -299,7 +288,6 @@ impl fmt::Debug for BufReader where R: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -410,7 +398,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -445,7 +432,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -460,7 +446,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -478,7 +463,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { + inner: Some(inner), +@@ -527,7 +511,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.as_ref().unwrap() } + + /// Gets a mutable reference to the underlying writer. +@@ -545,7 +528,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.as_mut().unwrap() } + + /// Returns a reference to the internally buffered data. +@@ -561,7 +543,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -585,7 +566,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -594,7 +574,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -630,7 +609,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufWriter") +@@ -640,7 +618,6 @@ impl fmt::Debug for BufWriter where W: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -650,7 +627,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -689,7 +665,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { &self.1 } + + /// Returns the buffered writer instance which generated the error. +@@ -722,23 +697,13 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { self.0 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { iie.1 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -809,7 +774,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -830,7 +794,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -851,7 +814,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { + inner: BufWriter::with_capacity(capacity, inner), +@@ -875,7 +837,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.get_ref() } + + /// Gets a mutable reference to the underlying writer. +@@ -898,7 +859,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.get_mut() } + + /// Unwraps this `LineWriter`, returning the underlying writer. +@@ -924,7 +884,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { +@@ -935,7 +894,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -980,7 +938,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("LineWriter") +diff --git a/cursor.rs b/cursor.rs +index a94176e..7768d39 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Initializer, SeekFrom, Error, ErrorKind, IoSlice, IoSliceMut}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { self.inner } + + /// Gets a reference to the underlying value in this cursor. +@@ -128,7 +125,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { &self.inner } + + /// Gets a mutable reference to the underlying value in this cursor. +@@ -147,7 +143,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { &mut self.inner } + + /// Returns the current position of this cursor. +@@ -169,7 +164,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { self.pos } + + /// Sets the position of this cursor. +@@ -189,11 +183,9 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { self.pos = pos; } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor where T: AsRef<[u8]> { + fn seek(&mut self, style: SeekFrom) -> io::Result { + let (base_pos, offset) = match style { +@@ -222,10 +214,9 @@ impl io::Seek for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor where T: AsRef<[u8]> { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -244,7 +235,7 @@ impl Read for Cursor where T: AsRef<[u8]> { + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -255,12 +246,16 @@ impl Read for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor where T: AsRef<[u8]> { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++impl Cursor where T: AsRef<[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor where T: AsRef<[u8]> { ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { self.get_buf() } + fn consume(&mut self, amt: usize) { self.pos += amt as u64; } + } + +@@ -292,6 +287,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new(ErrorKind::InvalidInput, +@@ -318,6 +314,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -331,7 +328,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -347,7 +343,7 @@ impl Write for Cursor<&mut [u8]> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -361,7 +357,7 @@ impl Write for Cursor<&mut Vec> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -375,8 +371,8 @@ impl Write for Cursor> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index c29a68e..c94d8c5 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,13 @@ +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; +-use crate::convert::From; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++use core::convert::Into; ++use core::fmt; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++use core::result; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; ++use core::convert::From; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +43,6 @@ use crate::convert::From; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +56,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +69,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +90,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +130,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +142,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +156,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +186,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -245,14 +230,13 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error +- where E: Into> ++ where E: Into + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { + repr: Repr::Custom(Box::new(Custom { + kind, +@@ -261,24 +245,6 @@ impl Error { + } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -304,7 +270,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -335,7 +300,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -369,12 +333,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error+Send+Sync+'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -440,12 +403,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error+Send+Sync+'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -474,8 +436,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -501,10 +462,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -516,22 +476,18 @@ impl fmt::Debug for Repr { + match *self { + Repr::Os(code) => + fmt.debug_struct("Os") +- .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)).finish(), ++ .field("code", &code).finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), + } + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -539,33 +495,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index c959f2d..b645bc8 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,13 +1,15 @@ +-use crate::cmp; +-use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, BufRead, Error, ErrorKind, +- IoSliceMut, IoSlice}; +-use crate::fmt; +-use crate::mem; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++use core::cmp; ++use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, Error, ErrorKind, IoSliceMut, IoSlice}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::fmt; ++use core::mem; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -24,11 +26,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -39,7 +43,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -62,12 +65,11 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -86,7 +88,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -103,11 +105,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -118,7 +122,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -141,12 +145,12 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -186,7 +190,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -245,6 +248,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -254,7 +258,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(*self) } +@@ -268,7 +272,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -307,7 +310,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index be364a1..abbf09f 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,50 +257,38 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::slice; +-use crate::str; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(feature="collections")] use collections::string::String; ++use core::str; ++#[cfg(feature="collections")] use collections::vec::Vec; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::slice; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++ ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Result, Error, ErrorKind}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, sink, Sink, empty, Empty, repeat, Repeat}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stdin, stdout, stderr, Stdin, Stdout, Stderr}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StdoutLock, StderrLock, StdinLock}; +-#[unstable(feature = "print_internals", issue = "0")] +-pub use self::stdio::{_print, _eprint}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; + + pub mod prelude; +-mod buffered; ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + mod util; +-mod stdio; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { buf: &'a mut Vec, len: usize } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { self.buf.set_len(self.len); } +@@ -325,6 +313,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where F: FnOnce(&mut Vec) -> Result + { +@@ -352,10 +341,12 @@ fn append_to_string(buf: &mut String, f: F) -> Result + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -497,7 +488,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -565,7 +555,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -576,7 +565,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -603,7 +591,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -656,7 +643,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -699,7 +686,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -762,7 +749,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -814,7 +800,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + + /// Transforms this `Read` instance to an [`Iterator`] over its bytes. +@@ -851,7 +836,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes where Self: Sized { + Bytes { inner: self } + } +@@ -886,7 +870,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain where Self: Sized { + Chain { first: self, second: next, done_first: false } + } +@@ -922,22 +905,64 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take where Self: Sized { + Take { inner: self, limit: limit } + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -950,10 +975,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -989,7 +1013,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1013,7 +1036,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1023,7 +1045,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1036,11 +1057,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1053,10 +1072,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1091,7 +1109,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(mem::replace(&mut bufs, &mut []), 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1115,7 +1132,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1126,13 +1142,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1146,21 +1160,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1214,7 +1225,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1263,7 +1273,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1274,7 +1283,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1302,7 +1310,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1335,7 +1342,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1387,7 +1393,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1443,7 +1448,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + } + +@@ -1473,7 +1477,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1489,7 +1492,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1527,7 +1529,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1566,7 +1567,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1578,29 +1578,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + -> Result { + let mut read = 0; +@@ -1680,7 +1677,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1721,7 +1718,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1743,7 +1739,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1799,7 +1794,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1858,7 +1852,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1899,7 +1892,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split where Self: Sized { + Split { buf: self, delim: byte } + } +@@ -1938,7 +1930,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines where Self: Sized { + Lines { buf: self } + } +@@ -1950,7 +1941,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -1976,7 +1966,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -1999,7 +1988,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2026,13 +2014,11 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain") +@@ -2042,7 +2028,6 @@ impl fmt::Debug for Chain { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2074,7 +2059,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2101,7 +2086,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2136,7 +2120,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { self.limit } + + /// Sets the number of bytes that can be read before this instance will +@@ -2162,7 +2145,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2187,7 +2169,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2212,7 +2193,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2241,13 +2221,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2265,6 +2243,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2273,7 +2252,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2300,13 +2279,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2330,14 +2307,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2362,13 +2339,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 2e19edf..66294a3 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Write, Seek}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{Read, Write, BufRead, Seek}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index 33cc87e..75b8032 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, Read, Initializer, Write, ErrorKind, BufRead, IoSlice, IoSliceMut}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, Read, Initializer, Write, ErrorKind, IoSlice, IoSliceMut}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where R: Read, W: Write + { +@@ -70,7 +70,6 @@ pub fn copy(reader: &mut R, writer: &mut W) -> io::Result< + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { _priv: () } + + /// Constructs a new handle to an empty reader. +@@ -90,10 +89,8 @@ pub struct Empty { _priv: () } + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { Empty { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { Ok(0) } +@@ -103,7 +100,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(&[]) } +@@ -111,7 +109,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -124,7 +121,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { byte: u8 } + + /// Creates an instance of a reader that infinitely repeats one byte. +@@ -141,10 +137,8 @@ pub struct Repeat { byte: u8 } + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { Repeat { byte } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -169,7 +163,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -182,7 +175,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { _priv: () } + + /// Creates an instance of a writer which will successfully consume all data. +@@ -199,10 +191,8 @@ pub struct Sink { _priv: () } + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { Sink { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { Ok(buf.len()) } +@@ -217,7 +207,6 @@ impl Write for Sink { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/ea43e5e21d8aa61e00124f634a71325e6d3bfaa8.patch b/patches/ea43e5e21d8aa61e00124f634a71325e6d3bfaa8.patch new file mode 100644 index 0000000..b8855eb --- /dev/null +++ b/patches/ea43e5e21d8aa61e00124f634a71325e6d3bfaa8.patch @@ -0,0 +1,2078 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 987371f..d2af8b8 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,6 +1,7 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DEFAULT_BUF_SIZE}; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -42,7 +43,6 @@ use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DE + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -66,7 +66,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -87,7 +86,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -117,7 +115,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -140,7 +137,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -168,7 +164,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -191,7 +186,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -215,7 +209,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -233,7 +226,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -253,7 +245,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -309,7 +300,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -329,7 +319,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -342,7 +331,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index 65bc2fc..46cd6b8 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,9 +1,9 @@ +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; +-use crate::mem; ++use core::mem; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -65,7 +65,6 @@ use crate::mem; + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -87,7 +86,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -105,7 +103,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -200,7 +197,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -220,7 +216,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -238,7 +233,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -270,7 +264,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -294,7 +287,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -325,7 +317,6 @@ impl BufWriter { + /// assert_eq!(recovered_writer.len(), 0); + /// assert_eq!(&buffered_data.unwrap(), b"ata"); + /// ``` +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_raw_parts(mut self) -> (W, Result, WriterPanicked>) { + let buf = mem::take(&mut self.buf); + let buf = if !self.panicked { Ok(buf) } else { Err(WriterPanicked { buf }) }; +@@ -333,7 +324,6 @@ impl BufWriter { + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + /// Error returned for the buffered data from `BufWriter::into_raw_parts`, when the underlying + /// writer has previously panicked. Contains the (possibly partly written) buffered data. + /// +@@ -367,7 +357,6 @@ pub struct WriterPanicked { + impl WriterPanicked { + /// Returns the perhaps-unwritten data. Some of this data may have been written by the + /// panicking call(s) to the underlying writer, so simply writing it again is not a good idea. +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_inner(self) -> Vec { + self.buf + } +@@ -376,22 +365,12 @@ impl WriterPanicked { + "BufWriter inner writer panicked, what data remains unwritten is not known"; + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] +-impl error::Error for WriterPanicked { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- Self::DESCRIPTION +- } +-} +- +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Display for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + write!(f, "{}", Self::DESCRIPTION) + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Debug for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("WriterPanicked") +@@ -400,7 +379,6 @@ impl fmt::Debug for WriterPanicked { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -497,7 +475,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -510,7 +487,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -521,7 +497,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index d0c859d..a052adf 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index 6549781..0dc7440 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,7 +119,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } +@@ -143,7 +139,6 @@ impl IntoInnerError { + /// let err = into_inner_err.into_error(); + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_error(self) -> Error { + self.1 + } +@@ -167,28 +162,17 @@ impl IntoInnerError { + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// assert_eq!(recovered_writer.buffer(), b"t be actually written"); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_parts(self) -> (Error, W) { + (self.1, self.0) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/copy.rs b/copy.rs +index eb60df2..df99a47 100644 +--- a/copy.rs ++++ b/copy.rs +@@ -1,5 +1,6 @@ +-use super::{BufWriter, ErrorKind, Read, Result, Write, DEFAULT_BUF_SIZE}; +-use crate::mem::MaybeUninit; ++use super::{ErrorKind, Read, Result, Write, DEFAULT_BUF_SIZE}; ++#[cfg(feature = "collections")] use super::BufWriter; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,19 +40,12 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> Result + where + R: Read, + W: Write, + { +- cfg_if::cfg_if! { +- if #[cfg(any(target_os = "linux", target_os = "android"))] { +- crate::sys::kernel_copy::copy_spec(reader, writer) +- } else { +- generic_copy(reader, writer) +- } +- } ++ generic_copy(reader, writer) + } + + /// The userspace read-write-loop implementation of `io::copy` that is used when +@@ -76,6 +70,7 @@ impl BufferedCopySpec for W { + } + } + ++#[cfg(feature = "collections")] + impl BufferedCopySpec for BufWriter { + fn copy_to(reader: &mut R, writer: &mut Self) -> Result { + if writer.capacity() < DEFAULT_BUF_SIZE { +diff --git a/cursor.rs b/cursor.rs +index bbee2cc..dc75216 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,8 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,8 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn get_ref(&self) -> &T { + &self.inner + } +@@ -152,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -176,8 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn position(&self) -> u64 { + self.pos + } +@@ -199,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -245,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -274,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -285,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -326,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -354,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -366,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -389,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -410,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -431,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 00bf8b9..5c0e7cd 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -216,7 +222,6 @@ impl BufRead for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -279,6 +284,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -288,7 +294,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -310,7 +316,6 @@ impl BufRead for &[u8] { + /// If the number of bytes to be written exceeds the size of the slice, write operations will + /// return short writes: ultimately, `Ok(0)`; in this situation, `write_all` returns an error of + /// kind `ErrorKind::WriteZero`. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -356,7 +361,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index db3b0e2..6e3a4c5 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -246,58 +246,48 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::copy::copy; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[unstable(feature = "internal_output_capture", issue = "none")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::set_output_capture; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + pub(crate) mod copy; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -324,6 +314,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -351,10 +342,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -505,7 +498,6 @@ pub(crate) fn default_read_exact(this: &mut R, mut buf: &mut [ + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -576,7 +568,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -588,7 +579,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -601,7 +591,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -625,7 +614,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -677,7 +665,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -720,7 +708,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -784,7 +772,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, buf: &mut [u8]) -> Result<()> { + default_read_exact(self, buf) + } +@@ -823,7 +810,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -860,7 +846,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -898,7 +883,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -937,7 +921,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -987,29 +970,71 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +-#[unstable(feature = "io_read_to_string", issue = "80218")] ++#[cfg(feature="collections")] + pub fn read_to_string(reader: &mut R) -> Result { + let mut buf = String::new(); + reader.read_to_string(&mut buf)?; + Ok(buf) + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1022,10 +1047,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1060,7 +1084,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1084,7 +1107,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1094,7 +1116,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1107,18 +1128,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1131,10 +1148,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1168,7 +1184,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1192,7 +1207,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1203,13 +1217,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1223,21 +1235,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1291,7 +1300,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1338,7 +1346,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1351,7 +1358,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1366,7 +1372,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1394,7 +1399,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1428,7 +1432,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1490,7 +1493,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1543,7 +1545,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1599,7 +1600,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1634,7 +1634,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1648,7 +1647,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1685,7 +1683,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_stream_len", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1722,7 +1719,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "seek_convenience", since = "1.51.0")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1732,29 +1728,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1830,7 +1823,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1871,7 +1864,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1893,7 +1885,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1950,7 +1941,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -2013,7 +2003,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2051,7 +2040,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2088,7 +2076,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2103,7 +2090,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2129,7 +2115,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2152,7 +2137,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2179,20 +2163,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2220,7 +2201,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2245,7 +2226,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2278,7 +2258,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2306,7 +2285,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2331,7 +2309,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2356,7 +2333,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2385,13 +2361,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2409,6 +2383,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2417,7 +2392,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2444,13 +2419,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2474,14 +2447,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2506,13 +2479,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index d806431..6b9791a 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index e43ce4c..e1f6fbc 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,14 +3,14 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write}; ++use core::fmt; ++use crate::io::{self, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; + + /// A reader which is always at EOF. + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -30,13 +30,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -48,7 +45,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -58,7 +56,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "empty_seek", since = "1.51.0")] + impl Seek for Empty { + fn seek(&mut self, _pos: SeekFrom) -> io::Result { + Ok(0) +@@ -73,7 +70,6 @@ impl Seek for Empty { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -84,7 +80,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -103,13 +98,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -139,7 +131,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -150,7 +141,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -171,13 +161,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -201,7 +188,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -225,7 +211,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/ec2826cc2e0b3a800836bcf8733dee0924f6b7ab.patch b/patches/ec2826cc2e0b3a800836bcf8733dee0924f6b7ab.patch new file mode 100644 index 0000000..dadb273 --- /dev/null +++ b/patches/ec2826cc2e0b3a800836bcf8733dee0924f6b7ab.patch @@ -0,0 +1,1888 @@ +diff --git a/buffered.rs b/buffered.rs +index e986a39..e127e72 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -197,7 +191,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -221,7 +214,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -239,7 +231,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -259,7 +250,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -301,7 +291,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -321,7 +310,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -334,7 +322,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -445,7 +432,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -480,7 +466,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -495,7 +480,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -513,7 +497,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -560,7 +543,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -580,7 +562,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -598,7 +579,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -618,7 +598,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -642,7 +621,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -651,7 +629,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -691,7 +668,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -704,7 +680,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -714,7 +689,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -753,7 +727,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -788,28 +761,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -880,7 +842,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -901,7 +862,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -922,7 +882,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -943,7 +902,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -968,7 +926,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -996,7 +953,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -1004,7 +960,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1105,7 +1060,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index f3e3fc8..0e6fcdb 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -272,7 +263,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -283,15 +274,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -324,6 +324,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -352,6 +353,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -364,7 +366,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -387,7 +388,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -408,7 +409,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -429,8 +430,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index d80a388..8991308 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -432,12 +396,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -466,8 +429,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -493,10 +455,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -509,8 +470,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -518,13 +477,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -532,34 +489,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 01dff0b..eb78a0f 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -30,11 +34,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -45,7 +51,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -77,14 +82,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -107,7 +111,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -129,11 +133,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -144,7 +150,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -176,14 +182,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -227,7 +233,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -290,6 +295,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -299,7 +305,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -317,7 +323,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -363,7 +368,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 717d286..8a46366 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -258,54 +258,44 @@ + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + // ignore-tidy-filelength + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::mem; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++use core::mem; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -332,6 +322,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -359,10 +350,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -498,7 +491,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning + /// how many bytes were read. +@@ -570,7 +562,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -582,7 +573,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -595,7 +585,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -622,7 +611,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -675,7 +663,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -718,7 +706,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -781,7 +769,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -835,7 +822,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -877,7 +863,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -915,7 +900,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -954,7 +938,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -963,22 +946,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -991,10 +1016,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1029,7 +1053,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1053,7 +1076,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1063,7 +1085,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1076,18 +1097,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1100,10 +1117,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1137,7 +1153,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1161,7 +1176,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1172,13 +1186,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1192,21 +1204,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1260,7 +1269,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. + /// +@@ -1308,7 +1316,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1319,7 +1326,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1332,7 +1338,6 @@ pub trait Write { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1360,7 +1365,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1395,7 +1399,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1459,7 +1462,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + while !bufs.is_empty() { + match self.write_vectored(bufs) { +@@ -1512,7 +1514,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1568,7 +1569,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1603,7 +1603,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1619,7 +1618,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1657,7 +1655,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1696,7 +1693,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1708,29 +1704,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1809,7 +1802,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1850,7 +1843,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1872,7 +1864,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1932,7 +1923,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1995,7 +1985,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2036,7 +2025,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2078,7 +2066,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2093,7 +2080,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2119,7 +2105,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2142,7 +2127,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2169,20 +2153,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2210,7 +2191,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2235,7 +2216,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2270,7 +2250,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2298,7 +2277,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2323,7 +2301,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2348,7 +2325,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2377,13 +2353,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2401,6 +2375,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2409,7 +2384,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2436,13 +2411,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2466,14 +2439,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2498,13 +2471,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b9d5dc2..07d090e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -190,7 +184,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -203,7 +196,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -222,12 +214,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -251,7 +241,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/ecef6c7c809eba2a4eed5e281f19ab7331998c6f.patch b/patches/ecef6c7c809eba2a4eed5e281f19ab7331998c6f.patch new file mode 100644 index 0000000..e872be0 --- /dev/null +++ b/patches/ecef6c7c809eba2a4eed5e281f19ab7331998c6f.patch @@ -0,0 +1,1872 @@ +diff --git a/buffered.rs b/buffered.rs +index 16ca539..afa2586 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -222,7 +215,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -240,7 +232,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -260,7 +251,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -298,7 +288,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -318,7 +307,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -331,7 +319,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -442,7 +429,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -477,7 +463,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -492,7 +477,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -510,7 +494,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -557,7 +540,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -577,7 +559,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -595,7 +576,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -616,7 +596,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -640,7 +619,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -649,7 +627,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -685,7 +662,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -698,7 +674,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -708,7 +683,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -747,7 +721,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -782,28 +755,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -874,7 +836,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -895,7 +856,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -916,7 +876,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -937,7 +896,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -962,7 +920,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -990,7 +947,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -998,7 +954,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1099,7 +1054,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index f36aa18..89d0701 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -268,7 +259,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -279,15 +270,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -320,6 +320,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -348,6 +349,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -360,7 +362,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -378,7 +379,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -394,7 +395,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -410,8 +411,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index d80a388..8991308 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -432,12 +396,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -466,8 +429,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -493,10 +455,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -509,8 +470,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -518,13 +477,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -532,34 +489,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index b7f82e6..c857f83 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -25,11 +29,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -40,7 +46,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -67,14 +72,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -97,7 +101,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -114,11 +118,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -129,7 +135,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -156,14 +162,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -207,7 +213,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -265,6 +270,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -274,7 +280,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -292,7 +298,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -333,7 +338,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 5ab8826..028c5e8 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,54 +257,44 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::mem; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++use core::mem; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -331,6 +321,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -358,10 +349,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -497,7 +490,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning + /// how many bytes were read. +@@ -564,7 +556,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -575,7 +566,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -602,7 +592,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -655,7 +644,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -698,7 +687,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -761,7 +750,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -815,7 +803,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -857,7 +844,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -895,7 +881,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -934,7 +919,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -943,22 +927,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -971,10 +997,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1009,7 +1034,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1033,7 +1057,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1043,7 +1066,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1056,18 +1078,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1080,10 +1098,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1117,7 +1134,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1141,7 +1157,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1152,13 +1167,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1172,21 +1185,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1240,7 +1250,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. + /// +@@ -1288,7 +1297,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1299,7 +1307,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1327,7 +1334,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1362,7 +1368,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1426,7 +1431,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + while !bufs.is_empty() { + match self.write_vectored(bufs) { +@@ -1479,7 +1483,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1535,7 +1538,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1570,7 +1572,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1586,7 +1587,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1624,7 +1624,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1663,7 +1662,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1675,29 +1673,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1776,7 +1771,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1817,7 +1812,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1839,7 +1833,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1895,7 +1888,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1954,7 +1946,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1995,7 +1986,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2037,7 +2027,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2052,7 +2041,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2078,7 +2066,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2101,7 +2088,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2128,20 +2114,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2169,7 +2152,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2194,7 +2177,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2229,7 +2211,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2257,7 +2238,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2282,7 +2262,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2307,7 +2286,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2336,13 +2314,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2360,6 +2336,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2368,7 +2345,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2395,13 +2372,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2425,14 +2400,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2457,13 +2432,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b09161b..e52119e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -185,7 +179,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -217,12 +209,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -241,7 +231,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/edb5214b29cd7de06dd10f673986d38e568b077c.patch b/patches/edb5214b29cd7de06dd10f673986d38e568b077c.patch new file mode 100644 index 0000000..78d8564 --- /dev/null +++ b/patches/edb5214b29cd7de06dd10f673986d38e568b077c.patch @@ -0,0 +1,1797 @@ +diff --git a/buffered.rs b/buffered.rs +index aaf628e..259eba3 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,13 +1,13 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, Initializer, DEFAULT_BUF_SIZE, Error, ErrorKind, SeekFrom, IoSlice, + IoSliceMut}; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -47,7 +47,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -71,7 +70,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -92,7 +90,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -127,7 +124,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { &self.inner } + + /// Gets a mutable reference to the underlying reader. +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { &mut self.inner } + + /// Returns a reference to the internally buffered data. +@@ -172,7 +167,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -195,7 +189,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { self.inner } + + /// Invalidates all data in the internal buffer. +@@ -211,7 +204,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -231,7 +223,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -269,7 +260,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -289,7 +279,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader where R: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufReader") +@@ -299,7 +288,6 @@ impl fmt::Debug for BufReader where R: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -408,7 +396,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -443,7 +430,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -458,7 +444,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -476,7 +461,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { + inner: Some(inner), +@@ -525,7 +509,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.as_ref().unwrap() } + + /// Gets a mutable reference to the underlying writer. +@@ -543,7 +526,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.as_mut().unwrap() } + + /// Returns a reference to the internally buffered data. +@@ -559,7 +541,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -583,7 +564,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -592,7 +572,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -628,7 +607,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("BufWriter") +@@ -638,7 +616,6 @@ impl fmt::Debug for BufWriter where W: fmt::Debug { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -648,7 +625,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -687,7 +663,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { &self.1 } + + /// Returns the buffered writer instance which generated the error. +@@ -720,23 +695,13 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { self.0 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { iie.1 } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -807,7 +772,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -828,7 +792,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -849,7 +812,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { + inner: BufWriter::with_capacity(capacity, inner), +@@ -873,7 +835,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { self.inner.get_ref() } + + /// Gets a mutable reference to the underlying writer. +@@ -896,7 +857,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { self.inner.get_mut() } + + /// Unwraps this `LineWriter`, returning the underlying writer. +@@ -922,7 +882,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { +@@ -933,7 +892,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -978,7 +936,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter where W: fmt::Debug { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt.debug_struct("LineWriter") +diff --git a/cursor.rs b/cursor.rs +index a94176e..7768d39 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Initializer, SeekFrom, Error, ErrorKind, IoSlice, IoSliceMut}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { self.inner } + + /// Gets a reference to the underlying value in this cursor. +@@ -128,7 +125,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { &self.inner } + + /// Gets a mutable reference to the underlying value in this cursor. +@@ -147,7 +143,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { &mut self.inner } + + /// Returns the current position of this cursor. +@@ -169,7 +164,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { self.pos } + + /// Sets the position of this cursor. +@@ -189,11 +183,9 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { self.pos = pos; } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor where T: AsRef<[u8]> { + fn seek(&mut self, style: SeekFrom) -> io::Result { + let (base_pos, offset) = match style { +@@ -222,10 +214,9 @@ impl io::Seek for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor where T: AsRef<[u8]> { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -244,7 +235,7 @@ impl Read for Cursor where T: AsRef<[u8]> { + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -255,12 +246,16 @@ impl Read for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor where T: AsRef<[u8]> { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++impl Cursor where T: AsRef<[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor where T: AsRef<[u8]> { ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { self.get_buf() } + fn consume(&mut self, amt: usize) { self.pos += amt as u64; } + } + +@@ -292,6 +287,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new(ErrorKind::InvalidInput, +@@ -318,6 +314,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -331,7 +328,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -347,7 +343,7 @@ impl Write for Cursor<&mut [u8]> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -361,7 +357,7 @@ impl Write for Cursor<&mut Vec> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -375,8 +371,8 @@ impl Write for Cursor> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index c29a68e..c94d8c5 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,13 @@ +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; +-use crate::convert::From; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++use core::convert::Into; ++use core::fmt; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++use core::result; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; ++use core::convert::From; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +43,6 @@ use crate::convert::From; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +56,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +69,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +90,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +130,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +142,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +156,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +186,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -245,14 +230,13 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error +- where E: Into> ++ where E: Into + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { + repr: Repr::Custom(Box::new(Custom { + kind, +@@ -261,24 +245,6 @@ impl Error { + } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -304,7 +270,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -335,7 +300,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -369,12 +333,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error+Send+Sync+'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -440,12 +403,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error+Send+Sync+'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -474,8 +436,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -501,10 +462,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -516,22 +476,18 @@ impl fmt::Debug for Repr { + match *self { + Repr::Os(code) => + fmt.debug_struct("Os") +- .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)).finish(), ++ .field("code", &code).finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), + } + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -539,33 +495,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index c959f2d..b645bc8 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,13 +1,15 @@ +-use crate::cmp; +-use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, BufRead, Error, ErrorKind, +- IoSliceMut, IoSlice}; +-use crate::fmt; +-use crate::mem; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++use core::cmp; ++use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, Error, ErrorKind, IoSliceMut, IoSlice}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::fmt; ++use core::mem; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -24,11 +26,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -39,7 +43,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -62,12 +65,11 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -86,7 +88,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -103,11 +105,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -118,7 +122,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { (**self).write(buf) } +@@ -141,12 +145,12 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { (**self).seek(pos) } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() } +@@ -186,7 +190,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -245,6 +248,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -254,7 +258,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(*self) } +@@ -268,7 +272,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -307,7 +310,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 5060f36..1b1112d 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,50 +257,38 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::slice; +-use crate::str; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(feature="collections")] use collections::string::String; ++use core::str; ++#[cfg(feature="collections")] use collections::vec::Vec; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::slice; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++ ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Result, Error, ErrorKind}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, sink, Sink, empty, Empty, repeat, Repeat}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stdin, stdout, stderr, Stdin, Stdout, Stderr}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StdoutLock, StderrLock, StdinLock}; +-#[unstable(feature = "print_internals", issue = "0")] +-pub use self::stdio::{_print, _eprint}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; + + pub mod prelude; +-mod buffered; ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + mod util; +-mod stdio; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { buf: &'a mut Vec, len: usize } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { self.buf.set_len(self.len); } +@@ -325,6 +313,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where F: FnOnce(&mut Vec) -> Result + { +@@ -352,10 +341,12 @@ fn append_to_string(buf: &mut String, f: F) -> Result + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -489,7 +480,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -557,7 +547,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -568,7 +557,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -595,7 +583,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -648,7 +635,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -691,7 +678,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -754,7 +741,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -806,7 +792,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + + /// Transforms this `Read` instance to an [`Iterator`] over its bytes. +@@ -843,7 +828,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes where Self: Sized { + Bytes { inner: self } + } +@@ -878,7 +862,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain where Self: Sized { + Chain { first: self, second: next, done_first: false } + } +@@ -914,22 +897,64 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take where Self: Sized { + Take { inner: self, limit: limit } + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -942,10 +967,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -981,7 +1005,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1005,7 +1028,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1015,7 +1037,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1028,11 +1049,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1045,10 +1064,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1083,7 +1101,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(mem::replace(&mut bufs, &mut []), 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1107,7 +1124,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1118,13 +1134,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1138,21 +1152,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1206,7 +1217,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1255,7 +1265,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1266,7 +1275,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1294,7 +1302,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1327,7 +1334,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1379,7 +1385,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1435,7 +1440,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self where Self: Sized { self } + } + +@@ -1465,7 +1469,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1481,7 +1484,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1519,7 +1521,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1558,7 +1559,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1570,29 +1570,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + -> Result { + let mut read = 0; +@@ -1672,7 +1669,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1713,7 +1710,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1735,7 +1731,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1791,7 +1786,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1850,7 +1844,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1891,7 +1884,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split where Self: Sized { + Split { buf: self, delim: byte } + } +@@ -1930,7 +1922,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines where Self: Sized { + Lines { buf: self } + } +@@ -1942,7 +1933,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -1968,7 +1958,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -1991,7 +1980,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2018,13 +2006,11 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain") +@@ -2034,7 +2020,6 @@ impl fmt::Debug for Chain { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2066,7 +2051,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2093,7 +2078,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2128,7 +2112,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { self.limit } + + /// Sets the number of bytes that can be read before this instance will +@@ -2154,7 +2137,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2179,7 +2161,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2204,7 +2185,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2233,13 +2213,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2257,6 +2235,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2265,7 +2244,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2292,13 +2271,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2322,14 +2299,14 @@ impl Iterator for Bytes { + /// `BufRead`. Please see the documentation of `split()` for more details. + /// + /// [split]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2354,13 +2331,13 @@ impl Iterator for Split { + /// `BufRead`. Please see the documentation of `lines()` for more details. + /// + /// [lines]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 2e19edf..66294a3 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Write, Seek}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{Read, Write, BufRead, Seek}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index 33cc87e..75b8032 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, Read, Initializer, Write, ErrorKind, BufRead, IoSlice, IoSliceMut}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, Read, Initializer, Write, ErrorKind, IoSlice, IoSliceMut}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where R: Read, W: Write + { +@@ -70,7 +70,6 @@ pub fn copy(reader: &mut R, writer: &mut W) -> io::Result< + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { _priv: () } + + /// Constructs a new handle to an empty reader. +@@ -90,10 +89,8 @@ pub struct Empty { _priv: () } + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { Empty { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { Ok(0) } +@@ -103,7 +100,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(&[]) } +@@ -111,7 +109,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -124,7 +121,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { byte: u8 } + + /// Creates an instance of a reader that infinitely repeats one byte. +@@ -141,10 +137,8 @@ pub struct Repeat { byte: u8 } + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { Repeat { byte } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -169,7 +163,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -182,7 +175,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { _priv: () } + + /// Creates an instance of a writer which will successfully consume all data. +@@ -199,10 +191,8 @@ pub struct Sink { _priv: () } + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { Sink { _priv: () } } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { Ok(buf.len()) } +@@ -217,7 +207,6 @@ impl Write for Sink { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/eefec8abda7cb8e8693aa876fbd1e21f2a6a5c2d.patch b/patches/eefec8abda7cb8e8693aa876fbd1e21f2a6a5c2d.patch new file mode 100644 index 0000000..b8855eb --- /dev/null +++ b/patches/eefec8abda7cb8e8693aa876fbd1e21f2a6a5c2d.patch @@ -0,0 +1,2078 @@ +diff --git a/buffered/bufreader.rs b/buffered/bufreader.rs +index 987371f..d2af8b8 100644 +--- a/buffered/bufreader.rs ++++ b/buffered/bufreader.rs +@@ -1,6 +1,7 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DEFAULT_BUF_SIZE}; ++use crate::io::prelude::*; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -42,7 +43,6 @@ use crate::io::{self, BufRead, Initializer, IoSliceMut, Read, Seek, SeekFrom, DE + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -66,7 +66,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -87,7 +86,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -117,7 +115,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -140,7 +137,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -168,7 +164,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -191,7 +186,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -215,7 +209,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -233,7 +226,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -253,7 +245,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -309,7 +300,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -329,7 +319,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -342,7 +331,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +diff --git a/buffered/bufwriter.rs b/buffered/bufwriter.rs +index 65bc2fc..46cd6b8 100644 +--- a/buffered/bufwriter.rs ++++ b/buffered/bufwriter.rs +@@ -1,9 +1,9 @@ +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, IntoInnerError, IoSlice, Seek, SeekFrom, Write, DEFAULT_BUF_SIZE, + }; +-use crate::mem; ++use core::mem; ++use crate::io::prelude::*; + + /// Wraps a writer and buffers its output. + /// +@@ -65,7 +65,6 @@ use crate::mem; + /// [`TcpStream::write`]: super::super::super::net::TcpStream::write + /// [`TcpStream`]: crate::net::TcpStream + /// [`flush`]: BufWriter::flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -87,7 +86,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -105,7 +103,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -200,7 +197,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -220,7 +216,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -238,7 +233,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -270,7 +264,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -294,7 +287,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError::new(self, e)), +@@ -325,7 +317,6 @@ impl BufWriter { + /// assert_eq!(recovered_writer.len(), 0); + /// assert_eq!(&buffered_data.unwrap(), b"ata"); + /// ``` +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_raw_parts(mut self) -> (W, Result, WriterPanicked>) { + let buf = mem::take(&mut self.buf); + let buf = if !self.panicked { Ok(buf) } else { Err(WriterPanicked { buf }) }; +@@ -333,7 +324,6 @@ impl BufWriter { + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + /// Error returned for the buffered data from `BufWriter::into_raw_parts`, when the underlying + /// writer has previously panicked. Contains the (possibly partly written) buffered data. + /// +@@ -367,7 +357,6 @@ pub struct WriterPanicked { + impl WriterPanicked { + /// Returns the perhaps-unwritten data. Some of this data may have been written by the + /// panicking call(s) to the underlying writer, so simply writing it again is not a good idea. +- #[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + pub fn into_inner(self) -> Vec { + self.buf + } +@@ -376,22 +365,12 @@ impl WriterPanicked { + "BufWriter inner writer panicked, what data remains unwritten is not known"; + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] +-impl error::Error for WriterPanicked { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- Self::DESCRIPTION +- } +-} +- +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Display for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + write!(f, "{}", Self::DESCRIPTION) + } + } + +-#[unstable(feature = "bufwriter_into_raw_parts", issue = "80690")] + impl fmt::Debug for WriterPanicked { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("WriterPanicked") +@@ -400,7 +379,6 @@ impl fmt::Debug for WriterPanicked { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -497,7 +475,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -510,7 +487,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -521,7 +497,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +diff --git a/buffered/linewriter.rs b/buffered/linewriter.rs +index 502c6e3..3d6e7e9 100644 +--- a/buffered/linewriter.rs ++++ b/buffered/linewriter.rs +@@ -1,4 +1,4 @@ +-use crate::fmt; ++use core::fmt; + use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSlice, Write}; + + /// Wraps a writer and buffers output to it, flushing whenever a newline +@@ -63,7 +63,6 @@ use crate::io::{self, buffered::LineWriterShim, BufWriter, IntoInnerError, IoSli + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + } +@@ -83,7 +82,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -104,7 +102,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner) } + } +@@ -125,7 +122,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -150,7 +146,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -178,13 +173,11 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|err| err.new_wrapped(|inner| LineWriter { inner })) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + LineWriterShim::new(&mut self.inner).write(buf) +@@ -215,7 +208,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/buffered/linewritershim.rs b/buffered/linewritershim.rs +index d0c859d..a052adf 100644 +--- a/buffered/linewritershim.rs ++++ b/buffered/linewritershim.rs +@@ -1,5 +1,5 @@ + use crate::io::{self, BufWriter, IoSlice, Write}; +-use crate::memchr; ++use crate::io::memchr; + + /// Private helper struct for implementing the line-buffered writing logic. + /// This shim temporarily wraps a BufWriter, and uses its internals to +diff --git a/buffered/mod.rs b/buffered/mod.rs +index 6549781..0dc7440 100644 +--- a/buffered/mod.rs ++++ b/buffered/mod.rs +@@ -8,14 +8,13 @@ mod linewritershim; + #[cfg(test)] + mod tests; + +-use crate::error; +-use crate::fmt; ++use core::fmt; + use crate::io::Error; + +-pub use bufreader::BufReader; +-pub use bufwriter::BufWriter; +-pub use linewriter::LineWriter; +-use linewritershim::LineWriterShim; ++pub use self::bufreader::BufReader; ++pub use self::bufwriter::BufWriter; ++pub use self::linewriter::LineWriter; ++use self::linewritershim::LineWriterShim; + + /// An error returned by [`BufWriter::into_inner`] which combines an error that + /// happened while writing out the buffer, and the buffered writer object +@@ -42,7 +41,6 @@ use linewritershim::LineWriterShim; + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl IntoInnerError { +@@ -87,7 +85,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -122,7 +119,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } +@@ -143,7 +139,6 @@ impl IntoInnerError { + /// let err = into_inner_err.into_error(); + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_error(self) -> Error { + self.1 + } +@@ -167,28 +162,17 @@ impl IntoInnerError { + /// assert_eq!(err.kind(), ErrorKind::WriteZero); + /// assert_eq!(recovered_writer.buffer(), b"t be actually written"); + /// ``` +- #[unstable(feature = "io_into_inner_error_parts", issue = "79704")] + pub fn into_parts(self) -> (Error, W) { + (self.1, self.0) + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +diff --git a/copy.rs b/copy.rs +index eb60df2..df99a47 100644 +--- a/copy.rs ++++ b/copy.rs +@@ -1,5 +1,6 @@ +-use super::{BufWriter, ErrorKind, Read, Result, Write, DEFAULT_BUF_SIZE}; +-use crate::mem::MaybeUninit; ++use super::{ErrorKind, Read, Result, Write, DEFAULT_BUF_SIZE}; ++#[cfg(feature = "collections")] use super::BufWriter; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,19 +40,12 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> Result + where + R: Read, + W: Write, + { +- cfg_if::cfg_if! { +- if #[cfg(any(target_os = "linux", target_os = "android"))] { +- crate::sys::kernel_copy::copy_spec(reader, writer) +- } else { +- generic_copy(reader, writer) +- } +- } ++ generic_copy(reader, writer) + } + + /// The userspace read-write-loop implementation of `io::copy` that is used when +@@ -76,6 +70,7 @@ impl BufferedCopySpec for W { + } + } + ++#[cfg(feature = "collections")] + impl BufferedCopySpec for BufWriter { + fn copy_to(reader: &mut R, writer: &mut Self) -> Result { + if writer.capacity() < DEFAULT_BUF_SIZE { +diff --git a/cursor.rs b/cursor.rs +index bbee2cc..dc75216 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -3,10 +3,10 @@ mod tests; + + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -70,7 +70,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -93,8 +92,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +109,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,8 +126,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn get_ref(&self) -> &T { + &self.inner + } +@@ -152,7 +146,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -176,8 +169,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- #[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn position(&self) -> u64 { + self.pos + } +@@ -199,13 +190,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -245,13 +234,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -274,7 +262,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -285,15 +273,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -326,6 +323,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -354,6 +352,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -366,7 +365,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -389,7 +387,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -410,7 +408,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -431,8 +429,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index ba0f0a0..826f11d 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,11 +1,17 @@ + #[cfg(test)] + mod tests; + +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`] type for I/O operations. + /// +@@ -41,7 +47,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -54,12 +59,10 @@ pub type Result = result::Result; + /// [`Read`]: crate::io::Read + /// [`Write`]: crate::io::Write + /// [`Seek`]: crate::io::Seek +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -69,13 +72,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -87,48 +93,35 @@ struct Custom { + /// + /// [`io::Error`]: Error + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -140,10 +133,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: ErrorKind::InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -154,12 +145,10 @@ pub enum ErrorKind { + /// + /// [`write`]: crate::io::Write::write + /// [`Ok(0)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. + /// +@@ -167,7 +156,6 @@ pub enum ErrorKind { + /// [`ErrorKind`] variant in the future. It is not recommended to match + /// an error against `Other` and to expect any additional characteristics, + /// e.g., a specific [`Error::raw_os_error`] return value. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -176,7 +164,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -207,7 +194,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -247,36 +233,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// [`Error`] for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an [`Error`] from a particular OS error code. + /// + /// # Examples +@@ -302,7 +269,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -336,7 +302,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -372,12 +337,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -443,12 +407,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -479,8 +442,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -506,10 +468,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -522,8 +483,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -531,13 +490,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -545,34 +502,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 00bf8b9..5c0e7cd 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,17 +1,21 @@ + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -33,11 +37,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -48,7 +54,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -80,14 +85,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -110,7 +114,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -132,11 +136,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -147,7 +153,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -179,14 +185,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -216,7 +222,6 @@ impl BufRead for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -279,6 +284,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -288,7 +294,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -310,7 +316,6 @@ impl BufRead for &[u8] { + /// If the number of bytes to be written exceeds the size of the slice, write operations will + /// return short writes: ultimately, `Ok(0)`; in this situation, `write_all` returns an error of + /// kind `ErrorKind::WriteZero`. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -356,7 +361,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index db3b0e2..6e3a4c5 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -246,58 +246,48 @@ + //! [`Result`]: crate::result::Result + //! [`.unwrap()`]: crate::result::Result::unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- + #[cfg(test)] + mod tests; + +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::copy::copy; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[unstable(feature = "internal_output_capture", issue = "none")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::set_output_capture; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + pub(crate) mod copy; + mod cursor; + mod error; + mod impls; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -324,6 +314,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -351,10 +342,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -505,7 +498,6 @@ pub(crate) fn default_read_exact(this: &mut R, mut buf: &mut [ + /// [`std::io`]: self + /// [`File`]: crate::fs::File + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -576,7 +568,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -588,7 +579,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -601,7 +591,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -625,7 +614,6 @@ pub trait Read { + /// This method is unsafe because a `Read`er could otherwise return a + /// non-zeroing `Initializer` from another `Read` type without an `unsafe` + /// block. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -677,7 +665,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: crate::fs::read +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -720,7 +708,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: crate::fs::read_to_string +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -784,7 +772,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, buf: &mut [u8]) -> Result<()> { + default_read_exact(self, buf) + } +@@ -823,7 +810,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -860,7 +846,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -898,7 +883,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -937,7 +921,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -987,29 +970,71 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +-#[unstable(feature = "io_read_to_string", issue = "80218")] ++#[cfg(feature="collections")] + pub fn read_to_string(reader: &mut R) -> Result { + let mut buf = String::new(); + reader.read_to_string(&mut buf)?; + Ok(buf) + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1022,10 +1047,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1060,7 +1084,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1084,7 +1107,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1094,7 +1116,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1107,18 +1128,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1131,10 +1148,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1168,7 +1184,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1192,7 +1207,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1203,13 +1217,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1223,21 +1235,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1291,7 +1300,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: Write::write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1338,7 +1346,6 @@ pub trait Write { + /// ``` + /// + /// [`Ok(n)`]: Ok +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like [`write`], except that it writes from a slice of buffers. +@@ -1351,7 +1358,6 @@ pub trait Write { + /// buffer provided, or an empty one if none exists. + /// + /// [`write`]: Write::write +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1366,7 +1372,6 @@ pub trait Write { + /// The default implementation returns `false`. + /// + /// [`write_vectored`]: Write::write_vectored +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1394,7 +1399,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1428,7 +1432,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1490,7 +1493,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + // Guarantee that bufs is empty if it contains no data, + // to avoid calling write_vectored if there is no data to be written. +@@ -1543,7 +1545,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1599,7 +1600,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1634,7 +1634,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1648,7 +1647,6 @@ pub trait Seek { + /// # Errors + /// + /// Seeking to a negative offset is considered an error. +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1685,7 +1683,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_stream_len", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1722,7 +1719,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "seek_convenience", since = "1.51.0")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1732,29 +1728,26 @@ pub trait Seek { + /// + /// It is used by the [`Seek`] trait. + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1830,7 +1823,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1871,7 +1864,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1893,7 +1885,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: BufRead::fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1950,7 +1941,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -2013,7 +2003,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2051,7 +2040,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2088,7 +2076,6 @@ pub trait BufRead: Read { + /// # Errors + /// + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2103,7 +2090,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: Read::chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2129,7 +2115,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2152,7 +2137,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2179,20 +2163,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2220,7 +2201,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2245,7 +2226,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: Read::take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2278,7 +2258,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2306,7 +2285,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2331,7 +2309,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2356,7 +2333,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2385,13 +2361,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2409,6 +2383,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2417,7 +2392,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2444,13 +2419,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: Read::bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2474,14 +2447,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: BufRead::split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2506,13 +2479,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: BufRead::lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index d806431..6b9791a 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index e43ce4c..e1f6fbc 100644 +--- a/util.rs ++++ b/util.rs +@@ -3,14 +3,14 @@ + #[cfg(test)] + mod tests; + +-use crate::fmt; +-use crate::io::{self, BufRead, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write}; ++use core::fmt; ++use crate::io::{self, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; + + /// A reader which is always at EOF. + /// + /// This struct is generally created by calling [`empty()`]. Please see + /// the documentation of [`empty()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -30,13 +30,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -48,7 +45,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -58,7 +56,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "empty_seek", since = "1.51.0")] + impl Seek for Empty { + fn seek(&mut self, _pos: SeekFrom) -> io::Result { + Ok(0) +@@ -73,7 +70,6 @@ impl Seek for Empty { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -84,7 +80,6 @@ impl fmt::Debug for Empty { + /// + /// This struct is generally created by calling [`repeat()`]. Please + /// see the documentation of [`repeat()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -103,13 +98,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -139,7 +131,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -150,7 +141,6 @@ impl fmt::Debug for Repeat { + /// + /// This struct is generally created by calling [`sink`]. Please + /// see the documentation of [`sink()`] for more details. +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -171,13 +161,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] +-#[rustc_const_unstable(feature = "const_io_structs", issue = "78812")] + pub const fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -201,7 +188,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "write_mt", since = "1.48.0")] + impl Write for &Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -225,7 +211,6 @@ impl Write for &Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/f7256d28d1c2f8340ab5b99df4bdb15aa232f3f3.patch b/patches/f7256d28d1c2f8340ab5b99df4bdb15aa232f3f3.patch new file mode 100644 index 0000000..dcbe7c1 --- /dev/null +++ b/patches/f7256d28d1c2f8340ab5b99df4bdb15aa232f3f3.patch @@ -0,0 +1,1817 @@ +diff --git a/buffered.rs b/buffered.rs +index df259dc..3cb42f9 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -216,7 +209,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -236,7 +228,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -274,7 +265,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -294,7 +284,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -307,7 +296,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -418,7 +406,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -453,7 +440,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -468,7 +454,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -486,7 +471,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -533,7 +517,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -553,7 +536,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -571,7 +553,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -595,7 +576,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -604,7 +584,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -640,7 +619,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -653,7 +631,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -663,7 +640,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -702,7 +678,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -737,27 +712,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -828,7 +793,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -849,7 +813,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -870,7 +833,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -891,7 +853,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -916,7 +877,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -944,7 +904,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -952,7 +911,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1058,7 +1016,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index a94176e..7768d39 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Initializer, SeekFrom, Error, ErrorKind, IoSlice, IoSliceMut}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner: inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { self.inner } + + /// Gets a reference to the underlying value in this cursor. +@@ -128,7 +125,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { &self.inner } + + /// Gets a mutable reference to the underlying value in this cursor. +@@ -147,7 +143,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { &mut self.inner } + + /// Returns the current position of this cursor. +@@ -169,7 +164,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { self.pos } + + /// Sets the position of this cursor. +@@ -189,11 +183,9 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { self.pos = pos; } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor where T: AsRef<[u8]> { + fn seek(&mut self, style: SeekFrom) -> io::Result { + let (base_pos, offset) = match style { +@@ -222,10 +214,9 @@ impl io::Seek for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor where T: AsRef<[u8]> { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -244,7 +235,7 @@ impl Read for Cursor where T: AsRef<[u8]> { + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -255,12 +246,16 @@ impl Read for Cursor where T: AsRef<[u8]> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor where T: AsRef<[u8]> { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++impl Cursor where T: AsRef<[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor where T: AsRef<[u8]> { ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { self.get_buf() } + fn consume(&mut self, amt: usize) { self.pos += amt as u64; } + } + +@@ -292,6 +287,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new(ErrorKind::InvalidInput, +@@ -318,6 +314,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -331,7 +328,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -347,7 +343,7 @@ impl Write for Cursor<&mut [u8]> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -361,7 +357,7 @@ impl Write for Cursor<&mut Vec> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -375,8 +371,8 @@ impl Write for Cursor> { + fn flush(&mut self) -> io::Result<()> { Ok(()) } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index c20bd30..99af4d1 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -434,12 +398,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -468,8 +431,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -495,10 +457,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -511,8 +472,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -520,13 +479,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -534,33 +491,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index b7f82e6..c857f83 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -25,11 +29,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -40,7 +46,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -67,14 +72,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -97,7 +101,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -114,11 +118,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -129,7 +135,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -156,14 +162,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -207,7 +213,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -265,6 +270,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -274,7 +280,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -292,7 +298,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -333,7 +338,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 587ac24..04bc734 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -257,53 +257,43 @@ + //! [`Result`]: ../result/enum.Result.html + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -330,6 +320,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -357,10 +348,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -496,7 +489,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning +@@ -564,7 +556,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -575,7 +566,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -602,7 +592,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -655,7 +644,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -698,7 +687,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -761,7 +750,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -815,7 +803,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -857,7 +844,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -895,7 +881,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -934,7 +919,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -943,16 +927,59 @@ pub trait Read { + } + } + ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -965,10 +992,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1003,7 +1029,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1027,7 +1052,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1037,7 +1061,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1050,11 +1073,9 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1067,10 +1088,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1104,7 +1124,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1128,7 +1147,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1139,13 +1157,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1159,21 +1175,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1227,7 +1240,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + #[doc(spotlight)] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. +@@ -1276,7 +1288,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1287,7 +1298,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1315,7 +1325,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1348,7 +1357,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1401,7 +1409,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1457,7 +1464,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1492,7 +1498,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1508,7 +1513,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1546,7 +1550,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1585,7 +1588,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1597,29 +1599,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1698,7 +1697,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1739,7 +1738,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1761,7 +1759,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1817,7 +1814,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1876,7 +1872,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -1917,7 +1912,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -1959,7 +1953,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -1974,7 +1967,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2000,7 +1992,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2023,7 +2014,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2050,20 +2040,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2091,7 +2078,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2116,7 +2103,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2151,7 +2137,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2179,7 +2164,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2204,7 +2188,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2229,7 +2212,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2258,13 +2240,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2282,6 +2262,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2290,7 +2271,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2317,13 +2298,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2347,14 +2326,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2379,13 +2358,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b09161b..e52119e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -185,7 +179,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -198,7 +191,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -217,12 +209,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -241,7 +231,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/fb1aa5624dff1d96249080fe365ed794431f45db.patch b/patches/fb1aa5624dff1d96249080fe365ed794431f45db.patch new file mode 100644 index 0000000..e9313ca --- /dev/null +++ b/patches/fb1aa5624dff1d96249080fe365ed794431f45db.patch @@ -0,0 +1,1888 @@ +diff --git a/buffered.rs b/buffered.rs +index 046b1a6..2ad53d6 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -198,7 +192,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -222,7 +215,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -240,7 +232,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -260,7 +251,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -302,7 +292,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -322,7 +311,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -335,7 +323,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -446,7 +433,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -481,7 +467,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -496,7 +481,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -514,7 +498,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -561,7 +544,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -581,7 +563,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -599,7 +580,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -620,7 +600,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[unstable(feature = "buffered_io_capacity", issue = "68833")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -644,7 +623,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -653,7 +631,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -693,7 +670,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -706,7 +682,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -716,7 +691,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -755,7 +729,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -790,28 +763,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -882,7 +844,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -903,7 +864,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -924,7 +884,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -945,7 +904,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -970,7 +928,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -998,7 +955,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -1006,7 +962,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1107,7 +1062,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index f3e3fc8..0e6fcdb 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -272,7 +263,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -283,15 +274,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -324,6 +324,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -352,6 +353,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -364,7 +366,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -387,7 +388,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -408,7 +409,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -429,8 +430,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index d80a388..8991308 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -432,12 +396,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -466,8 +429,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -493,10 +455,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -509,8 +470,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -518,13 +477,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -532,34 +489,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 01dff0b..eb78a0f 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -30,11 +34,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -45,7 +51,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -77,14 +82,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -107,7 +111,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -129,11 +133,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -144,7 +150,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -176,14 +182,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -227,7 +233,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -290,6 +295,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -299,7 +305,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -317,7 +323,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -363,7 +368,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 36c6aa6..8a91d62 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -258,54 +258,44 @@ + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + // ignore-tidy-filelength + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::mem; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++use core::mem; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -332,6 +322,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -359,10 +350,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -498,7 +491,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning + /// how many bytes were read. +@@ -565,7 +557,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -577,7 +568,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -590,7 +580,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -617,7 +606,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -670,7 +658,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -713,7 +701,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -776,7 +764,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -830,7 +817,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -872,7 +858,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -910,7 +895,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -949,7 +933,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -958,22 +941,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -986,10 +1011,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1024,7 +1048,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1048,7 +1071,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1058,7 +1080,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1071,18 +1092,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1095,10 +1112,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1132,7 +1148,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1156,7 +1171,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1167,13 +1181,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1187,21 +1199,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1255,7 +1264,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. + /// +@@ -1303,7 +1311,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1314,7 +1321,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1327,7 +1333,6 @@ pub trait Write { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1355,7 +1360,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1390,7 +1394,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1454,7 +1457,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + while !bufs.is_empty() { + match self.write_vectored(bufs) { +@@ -1507,7 +1509,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1563,7 +1564,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1598,7 +1598,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1614,7 +1613,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1652,7 +1650,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1691,7 +1688,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1703,29 +1699,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1804,7 +1797,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1845,7 +1838,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1867,7 +1859,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1923,7 +1914,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1982,7 +1972,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2023,7 +2012,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2065,7 +2053,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2080,7 +2067,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2106,7 +2092,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2129,7 +2114,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2156,20 +2140,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2197,7 +2178,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2222,7 +2203,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2257,7 +2237,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2285,7 +2264,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2310,7 +2288,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2335,7 +2312,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2364,13 +2340,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2388,6 +2362,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2396,7 +2371,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2423,13 +2398,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2453,14 +2426,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2485,13 +2458,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b9d5dc2..07d090e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -190,7 +184,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -203,7 +196,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -222,12 +214,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -251,7 +241,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/patches/fff822fead6249671cbcb090b24bce58fab38de0.patch b/patches/fff822fead6249671cbcb090b24bce58fab38de0.patch new file mode 100644 index 0000000..961bd32 --- /dev/null +++ b/patches/fff822fead6249671cbcb090b24bce58fab38de0.patch @@ -0,0 +1,1888 @@ +diff --git a/buffered.rs b/buffered.rs +index 0737008..e5adb4b 100644 +--- a/buffered.rs ++++ b/buffered.rs +@@ -1,14 +1,14 @@ + //! Buffering wrappers for I/O traits + ++use core::prelude::v1::*; + use crate::io::prelude::*; + +-use crate::cmp; +-use crate::error; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ + self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE, + }; +-use crate::memchr; ++use crate::io::memchr; + + /// The `BufReader` struct adds buffering to any reader. + /// +@@ -50,7 +50,6 @@ use crate::memchr; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufReader { + inner: R, + buf: Box<[u8]>, +@@ -74,7 +73,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: R) -> BufReader { + BufReader::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -95,7 +93,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: R) -> BufReader { + unsafe { + let mut buffer = Vec::with_capacity(capacity); +@@ -125,7 +122,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &R { + &self.inner + } +@@ -148,7 +144,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut R { + &mut self.inner + } +@@ -174,7 +169,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf[self.pos..self.cap] + } +@@ -197,7 +191,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.len() + } +@@ -221,7 +214,6 @@ impl BufReader { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> R { + self.inner + } +@@ -239,7 +231,6 @@ impl BufReader { + /// the buffer will not be flushed, allowing for more efficient seeks. + /// This method does not return the location of the underlying reader, so the caller + /// must track this information themselves if it is required. +- #[unstable(feature = "bufreader_seek_relative", issue = "31100")] + pub fn seek_relative(&mut self, offset: i64) -> io::Result<()> { + let pos = self.pos as u64; + if offset < 0 { +@@ -259,7 +250,6 @@ impl BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for BufReader { + fn read(&mut self, buf: &mut [u8]) -> io::Result { + // If we don't have any buffered data and we're doing a massive read +@@ -301,7 +291,6 @@ impl Read for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl BufRead for BufReader { + fn fill_buf(&mut self) -> io::Result<&[u8]> { + // If we've reached the end of our internal buffer then we need to fetch +@@ -321,7 +310,6 @@ impl BufRead for BufReader { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufReader + where + R: fmt::Debug, +@@ -334,7 +322,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufReader { + /// Seek to an offset, in bytes, in the underlying reader. + /// +@@ -445,7 +432,6 @@ impl Seek for BufReader { + /// [`TcpStream::write`]: ../../std/net/struct.TcpStream.html#method.write + /// [`TcpStream`]: ../../std/net/struct.TcpStream.html + /// [`flush`]: #method.flush +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct BufWriter { + inner: Option, + buf: Vec, +@@ -480,7 +466,6 @@ pub struct BufWriter { + /// }; + /// ``` + #[derive(Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct IntoInnerError(W, Error); + + impl BufWriter { +@@ -495,7 +480,6 @@ impl BufWriter { + /// + /// let mut buffer = BufWriter::new(TcpStream::connect("127.0.0.1:34254").unwrap()); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> BufWriter { + BufWriter::with_capacity(DEFAULT_BUF_SIZE, inner) + } +@@ -513,7 +497,6 @@ impl BufWriter { + /// let stream = TcpStream::connect("127.0.0.1:34254").unwrap(); + /// let mut buffer = BufWriter::with_capacity(100, stream); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> BufWriter { + BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false } + } +@@ -560,7 +543,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.as_ref().unwrap() + } +@@ -580,7 +562,6 @@ impl BufWriter { + /// // we can use reference just like buffer + /// let reference = buffer.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.as_mut().unwrap() + } +@@ -598,7 +579,6 @@ impl BufWriter { + /// // See how many bytes are currently buffered + /// let bytes_buffered = buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "bufreader_buffer", since = "1.37.0")] + pub fn buffer(&self) -> &[u8] { + &self.buf + } +@@ -618,7 +598,6 @@ impl BufWriter { + /// // Calculate how many bytes can be written without flushing + /// let without_flush = capacity - buf_writer.buffer().len(); + /// ``` +- #[stable(feature = "buffered_io_capacity", since = "1.46.0")] + pub fn capacity(&self) -> usize { + self.buf.capacity() + } +@@ -642,7 +621,6 @@ impl BufWriter { + /// // unwrap the TcpStream and flush the buffer + /// let stream = buffer.into_inner().unwrap(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(mut self) -> Result>> { + match self.flush_buf() { + Err(e) => Err(IntoInnerError(self, e)), +@@ -651,7 +629,6 @@ impl BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for BufWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.buf.len() + buf.len() > self.buf.capacity() { +@@ -691,7 +668,6 @@ impl Write for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for BufWriter + where + W: fmt::Debug, +@@ -704,7 +680,6 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for BufWriter { + /// Seek to the offset, in bytes, in the underlying writer. + /// +@@ -714,7 +689,6 @@ impl Seek for BufWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Drop for BufWriter { + fn drop(&mut self) { + if self.inner.is_some() && !self.panicked { +@@ -753,7 +727,6 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn error(&self) -> &Error { + &self.1 + } +@@ -788,28 +761,17 @@ impl IntoInnerError { + /// } + /// }; + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> W { + self.0 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl From> for Error { + fn from(iie: IntoInnerError) -> Error { + iie.1 + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for IntoInnerError { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- error::Error::description(self.error()) +- } +-} +- +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for IntoInnerError { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.error().fmt(f) +@@ -880,7 +842,6 @@ impl fmt::Display for IntoInnerError { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct LineWriter { + inner: BufWriter, + need_flush: bool, +@@ -901,7 +862,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: W) -> LineWriter { + // Lines typically aren't that long, don't use a giant buffer + LineWriter::with_capacity(1024, inner) +@@ -922,7 +882,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn with_capacity(capacity: usize, inner: W) -> LineWriter { + LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false } + } +@@ -943,7 +902,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &W { + self.inner.get_ref() + } +@@ -968,7 +926,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut W { + self.inner.get_mut() + } +@@ -996,7 +953,6 @@ impl LineWriter { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> Result>> { + self.inner.into_inner().map_err(|IntoInnerError(buf, e)| { + IntoInnerError(LineWriter { inner: buf, need_flush: false }, e) +@@ -1004,7 +960,6 @@ impl LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for LineWriter { + fn write(&mut self, buf: &[u8]) -> io::Result { + if self.need_flush { +@@ -1105,7 +1060,6 @@ impl Write for LineWriter { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for LineWriter + where + W: fmt::Debug, +diff --git a/cursor.rs b/cursor.rs +index f4db5f8..4f20b8a 100644 +--- a/cursor.rs ++++ b/cursor.rs +@@ -1,9 +1,9 @@ + use crate::io::prelude::*; + +-use crate::cmp; ++use core::cmp; + use crate::io::{self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom}; + +-use core::convert::TryInto; ++#[cfg(feature="collections")] use core::convert::TryInto; + + /// A `Cursor` wraps an in-memory buffer and provides it with a + /// [`Seek`] implementation. +@@ -71,7 +71,6 @@ use core::convert::TryInto; + /// assert_eq!(&buff.get_ref()[5..15], &[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Clone, Debug, Default, Eq, PartialEq)] + pub struct Cursor { + inner: T, +@@ -94,7 +93,6 @@ impl Cursor { + /// # fn force_inference(_: &Cursor>) {} + /// # force_inference(&buff); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(inner: T) -> Cursor { + Cursor { pos: 0, inner } + } +@@ -112,7 +110,6 @@ impl Cursor { + /// + /// let vec = buff.into_inner(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -130,7 +127,6 @@ impl Cursor { + /// + /// let reference = buff.get_ref(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -151,7 +147,6 @@ impl Cursor { + /// + /// let reference = buff.get_mut(); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } +@@ -175,7 +170,6 @@ impl Cursor { + /// buff.seek(SeekFrom::Current(-1)).unwrap(); + /// assert_eq!(buff.position(), 1); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn position(&self) -> u64 { + self.pos + } +@@ -197,13 +191,11 @@ impl Cursor { + /// buff.set_position(4); + /// assert_eq!(buff.position(), 4); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn set_position(&mut self, pos: u64) { + self.pos = pos; + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl io::Seek for Cursor + where + T: AsRef<[u8]>, +@@ -243,13 +235,12 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Cursor + where + T: AsRef<[u8]>, + { + fn read(&mut self, buf: &mut [u8]) -> io::Result { +- let n = Read::read(&mut self.fill_buf()?, buf)?; ++ let n = Read::read(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(n) + } +@@ -272,7 +263,7 @@ where + + fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> { + let n = buf.len(); +- Read::read_exact(&mut self.fill_buf()?, buf)?; ++ Read::read_exact(&mut self.get_buf()?, buf)?; + self.pos += n as u64; + Ok(()) + } +@@ -283,15 +274,24 @@ where + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl BufRead for Cursor ++impl Cursor + where + T: AsRef<[u8]>, + { +- fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ fn get_buf(&mut self) -> io::Result<&[u8]> { + let amt = cmp::min(self.pos, self.inner.as_ref().len() as u64); + Ok(&self.inner.as_ref()[(amt as usize)..]) + } ++} ++ ++#[cfg(feature="collections")] ++impl BufRead for Cursor ++where ++ T: AsRef<[u8]>, ++{ ++ fn fill_buf(&mut self) -> io::Result<&[u8]> { ++ self.get_buf() ++ } + fn consume(&mut self, amt: usize) { + self.pos += amt as u64; + } +@@ -324,6 +324,7 @@ fn slice_write_vectored( + } + + // Resizing write implementation ++#[cfg(feature="collections")] + fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result { + let pos: usize = (*pos_mut).try_into().map_err(|_| { + Error::new( +@@ -352,6 +353,7 @@ fn vec_write(pos_mut: &mut u64, vec: &mut Vec, buf: &[u8]) -> io::Result, +@@ -364,7 +366,6 @@ fn vec_write_vectored( + Ok(nwritten) + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Cursor<&mut [u8]> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -387,7 +388,7 @@ impl Write for Cursor<&mut [u8]> { + } + } + +-#[stable(feature = "cursor_mut_vec", since = "1.25.0")] ++#[cfg(feature="collections")] + impl Write for Cursor<&mut Vec> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, self.inner, buf) +@@ -408,7 +409,7 @@ impl Write for Cursor<&mut Vec> { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature = "collections")] + impl Write for Cursor> { + fn write(&mut self, buf: &[u8]) -> io::Result { + vec_write(&mut self.pos, &mut self.inner, buf) +@@ -429,8 +430,8 @@ impl Write for Cursor> { + } + } + +-#[stable(feature = "cursor_box_slice", since = "1.5.0")] +-impl Write for Cursor> { ++#[cfg(feature = "alloc")] ++impl Write for Cursor<::alloc::boxed::Box<[u8]>> { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { + slice_write(&mut self.pos, &mut self.inner, buf) +diff --git a/error.rs b/error.rs +index d80a388..8991308 100644 +--- a/error.rs ++++ b/error.rs +@@ -1,8 +1,14 @@ +-use crate::convert::From; +-use crate::error; +-use crate::fmt; +-use crate::result; +-use crate::sys; ++use core::convert::From; ++use core::fmt; ++use core::result; ++ ++use core::convert::Into; ++use core::marker::{Send, Sync}; ++use core::option::Option::{self, Some, None}; ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(not(feature="alloc"))] use ::FakeBox as Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(not(feature="collections"))] use ::ErrorString as String; + + /// A specialized [`Result`](../result/enum.Result.html) type for I/O + /// operations. +@@ -38,7 +44,6 @@ use crate::sys; + /// Ok(buffer) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub type Result = result::Result; + + /// The error type for I/O operations of the [`Read`], [`Write`], [`Seek`], and +@@ -52,12 +57,10 @@ pub type Result = result::Result; + /// [`Write`]: ../io/trait.Write.html + /// [`Seek`]: ../io/trait.Seek.html + /// [`ErrorKind`]: enum.ErrorKind.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Error { + repr: Repr, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Debug for Error { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.repr, f) +@@ -67,13 +70,16 @@ impl fmt::Debug for Error { + enum Repr { + Os(i32), + Simple(ErrorKind), ++ #[cfg(feature="alloc")] + Custom(Box), ++ #[cfg(not(feature="alloc"))] ++ Custom(Custom), + } + + #[derive(Debug)] + struct Custom { + kind: ErrorKind, +- error: Box, ++ error: String, + } + + /// A list specifying general categories of I/O error. +@@ -85,48 +91,35 @@ struct Custom { + /// + /// [`io::Error`]: struct.Error.html + #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +-#[stable(feature = "rust1", since = "1.0.0")] + #[allow(deprecated)] + #[non_exhaustive] + pub enum ErrorKind { + /// An entity was not found, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + NotFound, + /// The operation lacked the necessary privileges to complete. +- #[stable(feature = "rust1", since = "1.0.0")] + PermissionDenied, + /// The connection was refused by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionRefused, + /// The connection was reset by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionReset, + /// The connection was aborted (terminated) by the remote server. +- #[stable(feature = "rust1", since = "1.0.0")] + ConnectionAborted, + /// The network operation failed because it was not connected yet. +- #[stable(feature = "rust1", since = "1.0.0")] + NotConnected, + /// A socket address could not be bound because the address is already in + /// use elsewhere. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrInUse, + /// A nonexistent interface was requested or the requested address was not + /// local. +- #[stable(feature = "rust1", since = "1.0.0")] + AddrNotAvailable, + /// The operation failed because a pipe was closed. +- #[stable(feature = "rust1", since = "1.0.0")] + BrokenPipe, + /// An entity already exists, often a file. +- #[stable(feature = "rust1", since = "1.0.0")] + AlreadyExists, + /// The operation needs to block to complete, but the blocking operation was + /// requested to not occur. +- #[stable(feature = "rust1", since = "1.0.0")] + WouldBlock, + /// A parameter was incorrect. +- #[stable(feature = "rust1", since = "1.0.0")] + InvalidInput, + /// Data not valid for the operation were encountered. + /// +@@ -138,10 +131,8 @@ pub enum ErrorKind { + /// `InvalidData` if the file's contents are not valid UTF-8. + /// + /// [`InvalidInput`]: #variant.InvalidInput +- #[stable(feature = "io_invalid_data", since = "1.2.0")] + InvalidData, + /// The I/O operation's timeout expired, causing it to be canceled. +- #[stable(feature = "rust1", since = "1.0.0")] + TimedOut, + /// An error returned when an operation could not be completed because a + /// call to [`write`] returned [`Ok(0)`]. +@@ -152,15 +143,12 @@ pub enum ErrorKind { + /// + /// [`write`]: ../../std/io/trait.Write.html#tymethod.write + /// [`Ok(0)`]: ../../std/io/type.Result.html +- #[stable(feature = "rust1", since = "1.0.0")] + WriteZero, + /// This operation was interrupted. + /// + /// Interrupted operations can typically be retried. +- #[stable(feature = "rust1", since = "1.0.0")] + Interrupted, + /// Any I/O error not part of this list. +- #[stable(feature = "rust1", since = "1.0.0")] + Other, + + /// An error returned when an operation could not be completed because an +@@ -169,7 +157,6 @@ pub enum ErrorKind { + /// This typically means that an operation could only succeed if it read a + /// particular number of bytes but only a smaller number of bytes could be + /// read. +- #[stable(feature = "read_exact", since = "1.6.0")] + UnexpectedEof, + } + +@@ -200,7 +187,6 @@ impl ErrorKind { + + /// Intended for use for errors not exposed to the user, where allocating onto + /// the heap (for normal construction via Error::new) is too costly. +-#[stable(feature = "io_error_from_errorkind", since = "1.14.0")] + impl From for Error { + /// Converts an [`ErrorKind`] into an [`Error`]. + /// +@@ -243,36 +229,17 @@ impl Error { + /// // errors can also be created from other errors + /// let custom_error2 = Error::new(ErrorKind::Interrupted, custom_error); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn new(kind: ErrorKind, error: E) -> Error + where +- E: Into>, ++ E: Into, + { + Self::_new(kind, error.into()) + } + +- fn _new(kind: ErrorKind, error: Box) -> Error { ++ fn _new(kind: ErrorKind, error: String) -> Error { + Error { repr: Repr::Custom(Box::new(Custom { kind, error })) } + } + +- /// Returns an error representing the last OS error which occurred. +- /// +- /// This function reads the value of `errno` for the target platform (e.g. +- /// `GetLastError` on Windows) and will return a corresponding instance of +- /// `Error` for the error code. +- /// +- /// # Examples +- /// +- /// ``` +- /// use std::io::Error; +- /// +- /// println!("last OS error: {:?}", Error::last_os_error()); +- /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] +- pub fn last_os_error() -> Error { +- Error::from_raw_os_error(sys::os::errno() as i32) +- } +- + /// Creates a new instance of an `Error` from a particular OS error code. + /// + /// # Examples +@@ -298,7 +265,6 @@ impl Error { + /// assert_eq!(error.kind(), io::ErrorKind::InvalidInput); + /// # } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn from_raw_os_error(code: i32) -> Error { + Error { repr: Repr::Os(code) } + } +@@ -329,7 +295,6 @@ impl Error { + /// print_os_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn raw_os_error(&self) -> Option { + match self.repr { + Repr::Os(i) => Some(i), +@@ -363,12 +328,11 @@ impl Error { + /// print_error(&Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_ref(&self) -> Option<&String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref c) => Some(&*c.error), ++ Repr::Custom(ref c) => Some(&c.error), + } + } + +@@ -432,12 +396,11 @@ impl Error { + /// print_error(&change_error(Error::new(ErrorKind::Other, MyError::new()))); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> { ++ pub fn get_mut(&mut self) -> Option<&mut String> { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +- Repr::Custom(ref mut c) => Some(&mut *c.error), ++ Repr::Custom(ref mut c) => Some(&mut c.error), + } + } + +@@ -466,8 +429,7 @@ impl Error { + /// print_error(Error::new(ErrorKind::Other, "oh no!")); + /// } + /// ``` +- #[stable(feature = "io_error_inner", since = "1.3.0")] +- pub fn into_inner(self) -> Option> { ++ pub fn into_inner(self) -> Option { + match self.repr { + Repr::Os(..) => None, + Repr::Simple(..) => None, +@@ -493,10 +455,9 @@ impl Error { + /// print_error(Error::new(ErrorKind::AddrInUse, "oh no!")); + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn kind(&self) -> ErrorKind { + match self.repr { +- Repr::Os(code) => sys::decode_error_kind(code), ++ Repr::Os(_code) => ErrorKind::Other, + Repr::Custom(ref c) => c.kind, + Repr::Simple(kind) => kind, + } +@@ -509,8 +470,6 @@ impl fmt::Debug for Repr { + Repr::Os(code) => fmt + .debug_struct("Os") + .field("code", &code) +- .field("kind", &sys::decode_error_kind(code)) +- .field("message", &sys::os::error_string(code)) + .finish(), + Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt), + Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(), +@@ -518,13 +477,11 @@ impl fmt::Debug for Repr { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl fmt::Display for Error { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + match self.repr { + Repr::Os(code) => { +- let detail = sys::os::error_string(code); +- write!(fmt, "{} (os error {})", detail, code) ++ write!(fmt, "os error {}", code) + } + Repr::Custom(ref c) => c.error.fmt(fmt), + Repr::Simple(kind) => write!(fmt, "{}", kind.as_str()), +@@ -532,34 +489,6 @@ impl fmt::Display for Error { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] +-impl error::Error for Error { +- #[allow(deprecated, deprecated_in_future)] +- fn description(&self) -> &str { +- match self.repr { +- Repr::Os(..) | Repr::Simple(..) => self.kind().as_str(), +- Repr::Custom(ref c) => c.error.description(), +- } +- } +- +- #[allow(deprecated)] +- fn cause(&self) -> Option<&dyn error::Error> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.cause(), +- } +- } +- +- fn source(&self) -> Option<&(dyn error::Error + 'static)> { +- match self.repr { +- Repr::Os(..) => None, +- Repr::Simple(..) => None, +- Repr::Custom(ref c) => c.error.source(), +- } +- } +-} +- + fn _assert_error_is_sync_send() { + fn _is_sync_send() {} + _is_sync_send::(); +diff --git a/impls.rs b/impls.rs +index 01dff0b..eb78a0f 100644 +--- a/impls.rs ++++ b/impls.rs +@@ -1,14 +1,18 @@ +-use crate::cmp; +-use crate::fmt; ++use core::cmp; ++use core::fmt; + use crate::io::{ +- self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, ++ self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write, + }; +-use crate::mem; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem; ++ ++#[cfg(feature="alloc")] use alloc::boxed::Box; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; + + // ============================================================================= + // Forwarding implementations + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &mut R { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -30,11 +34,13 @@ impl Read for &mut R { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -45,7 +51,6 @@ impl Read for &mut R { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut W { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -77,14 +82,13 @@ impl Write for &mut W { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] + impl Seek for &mut S { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &mut B { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -107,7 +111,7 @@ impl BufRead for &mut B { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Read for Box { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -129,11 +133,13 @@ impl Read for Box { + (**self).initializer() + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + (**self).read_to_end(buf) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_string(&mut self, buf: &mut String) -> io::Result { + (**self).read_to_string(buf) +@@ -144,7 +150,7 @@ impl Read for Box { + (**self).read_exact(buf) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Write for Box { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -176,14 +182,14 @@ impl Write for Box { + (**self).write_fmt(fmt) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="alloc")] + impl Seek for Box { + #[inline] + fn seek(&mut self, pos: SeekFrom) -> io::Result { + (**self).seek(pos) + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Box { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -227,7 +233,6 @@ impl Write for Box { + /// + /// Note that reading updates the slice to point to the yet unread part. + /// The slice will be empty when EOF is reached. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for &[u8] { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -290,6 +295,7 @@ impl Read for &[u8] { + Ok(()) + } + ++ #[cfg(feature="collections")] + #[inline] + fn read_to_end(&mut self, buf: &mut Vec) -> io::Result { + buf.extend_from_slice(*self); +@@ -299,7 +305,7 @@ impl Read for &[u8] { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for &[u8] { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -317,7 +323,6 @@ impl BufRead for &[u8] { + /// + /// Note that writing updates the slice to point to the yet unwritten part. + /// The slice will be empty when it has been completely overwritten. +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for &mut [u8] { + #[inline] + fn write(&mut self, data: &[u8]) -> io::Result { +@@ -363,7 +368,7 @@ impl Write for &mut [u8] { + + /// Write is implemented for `Vec` by appending to the vector. + /// The vector will grow as needed. +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Write for Vec { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +diff --git a/mod.rs b/mod.rs +index 717d286..8a46366 100644 +--- a/mod.rs ++++ b/mod.rs +@@ -258,54 +258,44 @@ + //! [`.unwrap()`]: ../result/enum.Result.html#method.unwrap + // ignore-tidy-filelength + +-#![stable(feature = "rust1", since = "1.0.0")] +- +-use crate::cmp; +-use crate::fmt; +-use crate::mem; +-use crate::memchr; +-use crate::ops::{Deref, DerefMut}; +-use crate::ptr; +-use crate::slice; +-use crate::str; +-use crate::sys; +- +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::IntoInnerError; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::buffered::{BufReader, BufWriter, LineWriter}; +-#[stable(feature = "rust1", since = "1.0.0")] ++use core::cmp; ++use core::fmt; ++use core::mem; ++#[cfg(not(core_memchr))] ++mod memchr; ++#[cfg(all(feature="collections",core_memchr))] ++use core::slice::memchr; ++use core::ops::{Deref, DerefMut}; ++use core::ptr; ++use core::slice; ++use core::str; ++ ++#[cfg(feature="collections")] pub use self::buffered::IntoInnerError; ++#[cfg(feature="collections")] pub use self::buffered::{BufReader, BufWriter, LineWriter}; ++ + pub use self::cursor::Cursor; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::error::{Error, ErrorKind, Result}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout}; +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use self::stdio::{StderrLock, StdinLock, StdoutLock}; +-#[unstable(feature = "print_internals", issue = "none")] +-pub use self::stdio::{_eprint, _print}; +-#[unstable(feature = "libstd_io_internals", issue = "42788")] +-#[doc(no_inline, hidden)] +-pub use self::stdio::{set_panic, set_print}; +-#[stable(feature = "rust1", since = "1.0.0")] + pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink}; + +-mod buffered; ++#[cfg(feature="collections")] use collections::string::String; ++#[cfg(feature="collections")] use collections::vec::Vec; ++ ++#[cfg(feature="collections")] mod buffered; + mod cursor; + mod error; + mod impls; +-mod lazy; + pub mod prelude; +-mod stdio; + mod util; + +-const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE; ++const DEFAULT_BUF_SIZE: usize = 8 * 1024; + ++#[cfg(feature="collections")] + struct Guard<'a> { + buf: &'a mut Vec, + len: usize, + } + ++#[cfg(feature="collections")] + impl Drop for Guard<'_> { + fn drop(&mut self) { + unsafe { +@@ -332,6 +322,7 @@ impl Drop for Guard<'_> { + // 2. We're passing a raw buffer to the function `f`, and it is expected that + // the function only *appends* bytes to the buffer. We'll get undefined + // behavior if existing bytes are overwritten to have non-UTF-8 data. ++#[cfg(feature="collections")] + fn append_to_string(buf: &mut String, f: F) -> Result + where + F: FnOnce(&mut Vec) -> Result, +@@ -359,10 +350,12 @@ where + // + // Because we're extending the buffer with uninitialized data for trusted + // readers, we need to make sure to truncate that if any of this panics. ++#[cfg(feature="collections")] + fn read_to_end(r: &mut R, buf: &mut Vec) -> Result { + read_to_end_with_reservation(r, buf, |_| 32) + } + ++#[cfg(feature="collections")] + fn read_to_end_with_reservation( + r: &mut R, + buf: &mut Vec, +@@ -498,7 +491,6 @@ where + /// [`BufReader`]: struct.BufReader.html + /// [`&str`]: ../../std/primitive.str.html + /// [slice]: ../../std/primitive.slice.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Read { + /// Pull some bytes from this source into the specified buffer, returning + /// how many bytes were read. +@@ -570,7 +562,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read(&mut self, buf: &mut [u8]) -> Result; + + /// Like `read`, except that it reads into a slice of buffers. +@@ -582,7 +573,6 @@ pub trait Read { + /// + /// The default implementation calls `read` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result { + default_read_vectored(|b| self.read(b), bufs) + } +@@ -595,7 +585,6 @@ pub trait Read { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_read_vectored(&self) -> bool { + false + } +@@ -622,7 +611,6 @@ pub trait Read { + /// + /// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop + /// [`Initializer`]: ../../std/io/struct.Initializer.html +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + unsafe fn initializer(&self) -> Initializer { + Initializer::zeroing() +@@ -675,7 +663,7 @@ pub trait Read { + /// file.) + /// + /// [`std::fs::read`]: ../fs/fn.read.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + read_to_end(self, buf) + } +@@ -718,7 +706,7 @@ pub trait Read { + /// reading from a file.) + /// + /// [`std::fs::read_to_string`]: ../fs/fn.read_to_string.html +- #[stable(feature = "rust1", since = "1.0.0")] ++ #[cfg(feature="collections")] + fn read_to_string(&mut self, buf: &mut String) -> Result { + // Note that we do *not* call `.read_to_end()` here. We are passing + // `&mut Vec` (the raw contents of `buf`) into the `read_to_end` +@@ -781,7 +769,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "read_exact", since = "1.6.0")] + fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> { + while !buf.is_empty() { + match self.read(buf) { +@@ -835,7 +822,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -877,7 +863,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn bytes(self) -> Bytes + where + Self: Sized, +@@ -915,7 +900,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn chain(self, next: R) -> Chain + where + Self: Sized, +@@ -954,7 +938,6 @@ pub trait Read { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn take(self, limit: u64) -> Take + where + Self: Sized, +@@ -963,22 +946,64 @@ pub trait Read { + } + } + ++#[derive(Copy, Clone)] ++pub struct IoVecBuffer<'a>(&'a [u8]); ++ ++impl<'a> IoVecBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a [u8]) -> IoVecBuffer<'a> { ++ IoVecBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ self.0 = &self.0[n..] ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++} ++ ++pub struct IoVecMutBuffer<'a>(&'a mut [u8]); ++ ++impl<'a> IoVecMutBuffer<'a> { ++ #[inline] ++ pub fn new(buf: &'a mut [u8]) -> IoVecMutBuffer<'a> { ++ IoVecMutBuffer(buf) ++ } ++ ++ #[inline] ++ pub fn advance(&mut self, n: usize) { ++ let slice = core::mem::replace(&mut self.0, &mut []); ++ let (_, remaining) = slice.split_at_mut(n); ++ self.0 = remaining; ++ } ++ ++ #[inline] ++ pub fn as_slice(&self) -> &[u8] { ++ self.0 ++ } ++ ++ #[inline] ++ pub fn as_mut_slice(&mut self) -> &mut [u8] { ++ self.0 ++ } ++} ++ + /// A buffer type used with `Read::read_vectored`. + /// + /// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[repr(transparent)] +-pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>); ++pub struct IoSliceMut<'a>(IoVecMutBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSliceMut<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSliceMut<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSliceMut<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -991,10 +1016,9 @@ impl<'a> IoSliceMut<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> { +- IoSliceMut(sys::io::IoSliceMut::new(buf)) ++ IoSliceMut(IoVecMutBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1029,7 +1053,6 @@ impl<'a> IoSliceMut<'a> { + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); + /// ``` +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] { + // Number of buffers to remove. +@@ -1053,7 +1076,6 @@ impl<'a> IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSliceMut<'a> { + type Target = [u8]; + +@@ -1063,7 +1085,6 @@ impl<'a> Deref for IoSliceMut<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> DerefMut for IoSliceMut<'a> { + #[inline] + fn deref_mut(&mut self) -> &mut [u8] { +@@ -1076,18 +1097,14 @@ impl<'a> DerefMut for IoSliceMut<'a> { + /// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be + /// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on + /// Windows. +-#[stable(feature = "iovec", since = "1.36.0")] + #[derive(Copy, Clone)] + #[repr(transparent)] +-pub struct IoSlice<'a>(sys::io::IoSlice<'a>); ++pub struct IoSlice<'a>(IoVecBuffer<'a>); + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Send for IoSlice<'a> {} + +-#[stable(feature = "iovec-send-sync", since = "1.44.0")] + unsafe impl<'a> Sync for IoSlice<'a> {} + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> fmt::Debug for IoSlice<'a> { + fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(self.0.as_slice(), fmt) +@@ -1100,10 +1117,9 @@ impl<'a> IoSlice<'a> { + /// # Panics + /// + /// Panics on Windows if the slice is larger than 4GB. +- #[stable(feature = "iovec", since = "1.36.0")] + #[inline] + pub fn new(buf: &'a [u8]) -> IoSlice<'a> { +- IoSlice(sys::io::IoSlice::new(buf)) ++ IoSlice(IoVecBuffer::new(buf)) + } + + /// Advance the internal cursor of the slice. +@@ -1137,7 +1153,6 @@ impl<'a> IoSlice<'a> { + /// bufs = IoSlice::advance(bufs, 10); + /// assert_eq!(bufs[0].deref(), [2; 14].as_ref()); + /// assert_eq!(bufs[1].deref(), [3; 8].as_ref()); +- #[unstable(feature = "io_slice_advance", issue = "62726")] + #[inline] + pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] { + // Number of buffers to remove. +@@ -1161,7 +1176,6 @@ impl<'a> IoSlice<'a> { + } + } + +-#[stable(feature = "iovec", since = "1.36.0")] + impl<'a> Deref for IoSlice<'a> { + type Target = [u8]; + +@@ -1172,13 +1186,11 @@ impl<'a> Deref for IoSlice<'a> { + } + + /// A type used to conditionally initialize buffers passed to `Read` methods. +-#[unstable(feature = "read_initializer", issue = "42788")] + #[derive(Debug)] + pub struct Initializer(bool); + + impl Initializer { + /// Returns a new `Initializer` which will zero out buffers. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn zeroing() -> Initializer { + Initializer(true) +@@ -1192,21 +1204,18 @@ impl Initializer { + /// read from buffers passed to `Read` methods, and that the return value of + /// the method accurately reflects the number of bytes that have been + /// written to the head of the buffer. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub unsafe fn nop() -> Initializer { + Initializer(false) + } + + /// Indicates if a buffer should be initialized. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn should_initialize(&self) -> bool { + self.0 + } + + /// Initializes a buffer if necessary. +- #[unstable(feature = "read_initializer", issue = "42788")] + #[inline] + pub fn initialize(&self, buf: &mut [u8]) { + if self.should_initialize() { +@@ -1260,7 +1269,6 @@ impl Initializer { + /// `write` in a loop until its entire input has been written. + /// + /// [`write_all`]: #method.write_all +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Write { + /// Write a buffer into this writer, returning how many bytes were written. + /// +@@ -1308,7 +1316,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write(&mut self, buf: &[u8]) -> Result; + + /// Like `write`, except that it writes from a slice of buffers. +@@ -1319,7 +1326,6 @@ pub trait Write { + /// + /// The default implementation calls `write` with either the first nonempty + /// buffer provided, or an empty one if none exists. +- #[stable(feature = "iovec", since = "1.36.0")] + fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result { + default_write_vectored(|b| self.write(b), bufs) + } +@@ -1332,7 +1338,6 @@ pub trait Write { + /// and coalesce writes into a single buffer for higher performance. + /// + /// The default implementation returns `false`. +- #[unstable(feature = "can_vector", issue = "69941")] + fn is_write_vectored(&self) -> bool { + false + } +@@ -1360,7 +1365,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn flush(&mut self) -> Result<()>; + + /// Attempts to write an entire buffer into this writer. +@@ -1395,7 +1399,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_all(&mut self, mut buf: &[u8]) -> Result<()> { + while !buf.is_empty() { + match self.write(buf) { +@@ -1459,7 +1462,6 @@ pub trait Write { + /// assert_eq!(writer, &[1, 2, 3, 4, 5, 6]); + /// # Ok(()) } + /// ``` +- #[unstable(feature = "write_all_vectored", issue = "70436")] + fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> { + while !bufs.is_empty() { + match self.write_vectored(bufs) { +@@ -1512,7 +1514,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> { + // Create a shim which translates a Write to a fmt::Write and saves + // off I/O errors. instead of discarding them +@@ -1568,7 +1569,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn by_ref(&mut self) -> &mut Self + where + Self: Sized, +@@ -1603,7 +1603,6 @@ pub trait Write { + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub trait Seek { + /// Seek to an offset, in bytes, in a stream. + /// +@@ -1619,7 +1618,6 @@ pub trait Seek { + /// Seeking to a negative offset is considered an error. + /// + /// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start +- #[stable(feature = "rust1", since = "1.0.0")] + fn seek(&mut self, pos: SeekFrom) -> Result; + + /// Returns the length of this stream (in bytes). +@@ -1657,7 +1655,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_len(&mut self) -> Result { + let old_pos = self.stream_position()?; + let len = self.seek(SeekFrom::End(0))?; +@@ -1696,7 +1693,6 @@ pub trait Seek { + /// Ok(()) + /// } + /// ``` +- #[unstable(feature = "seek_convenience", issue = "59359")] + fn stream_position(&mut self) -> Result { + self.seek(SeekFrom::Current(0)) + } +@@ -1708,29 +1704,26 @@ pub trait Seek { + /// + /// [`Seek`]: trait.Seek.html + #[derive(Copy, PartialEq, Eq, Clone, Debug)] +-#[stable(feature = "rust1", since = "1.0.0")] + pub enum SeekFrom { + /// Sets the offset to the provided number of bytes. +- #[stable(feature = "rust1", since = "1.0.0")] +- Start(#[stable(feature = "rust1", since = "1.0.0")] u64), ++ Start(u64), + + /// Sets the offset to the size of this object plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- End(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ End(i64), + + /// Sets the offset to the current position plus the specified number of + /// bytes. + /// + /// It is possible to seek beyond the end of an object, but it's an error to + /// seek before byte 0. +- #[stable(feature = "rust1", since = "1.0.0")] +- Current(#[stable(feature = "rust1", since = "1.0.0")] i64), ++ Current(i64), + } + ++#[cfg(feature="collections")] + fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> Result { + let mut read = 0; + loop { +@@ -1809,7 +1802,7 @@ fn read_until(r: &mut R, delim: u8, buf: &mut Vec) -> R + /// } + /// ``` + /// +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + pub trait BufRead: Read { + /// Returns the contents of the internal buffer, filling it with more data + /// from the inner reader if it is empty. +@@ -1850,7 +1843,6 @@ pub trait BufRead: Read { + /// let length = buffer.len(); + /// stdin.consume(length); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn fill_buf(&mut self) -> Result<&[u8]>; + + /// Tells this buffer that `amt` bytes have been consumed from the buffer, +@@ -1872,7 +1864,6 @@ pub trait BufRead: Read { + /// that method's example includes an example of `consume()`. + /// + /// [`fill_buf`]: #tymethod.fill_buf +- #[stable(feature = "rust1", since = "1.0.0")] + fn consume(&mut self, amt: usize); + + /// Read all bytes into `buf` until the delimiter `byte` or EOF is reached. +@@ -1932,7 +1923,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, b""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_until(&mut self, byte: u8, buf: &mut Vec) -> Result { + read_until(self, byte, buf) + } +@@ -1995,7 +1985,6 @@ pub trait BufRead: Read { + /// assert_eq!(num_bytes, 0); + /// assert_eq!(buf, ""); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn read_line(&mut self, buf: &mut String) -> Result { + // Note that we are not calling the `.read_until` method here, but + // rather our hardcoded implementation. For more details as to why, see +@@ -2036,7 +2025,6 @@ pub trait BufRead: Read { + /// assert_eq!(split_iter.next(), Some(b"dolor".to_vec())); + /// assert_eq!(split_iter.next(), None); + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + fn split(self, byte: u8) -> Split + where + Self: Sized, +@@ -2078,7 +2066,6 @@ pub trait BufRead: Read { + /// Each line of the iterator has the same error semantics as [`BufRead::read_line`]. + /// + /// [`BufRead::read_line`]: trait.BufRead.html#method.read_line +- #[stable(feature = "rust1", since = "1.0.0")] + fn lines(self) -> Lines + where + Self: Sized, +@@ -2093,7 +2080,6 @@ pub trait BufRead: Read { + /// Please see the documentation of [`chain`] for more details. + /// + /// [`chain`]: trait.Read.html#method.chain +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Chain { + first: T, + second: U, +@@ -2119,7 +2105,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn into_inner(self) -> (T, U) { + (self.first, self.second) + } +@@ -2142,7 +2127,6 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> (&T, &U) { + (&self.first, &self.second) + } +@@ -2169,20 +2153,17 @@ impl Chain { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> (&mut T, &mut U) { + (&mut self.first, &mut self.second) + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Chain { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish() + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Chain { + fn read(&mut self, buf: &mut [u8]) -> Result { + if !self.done_first { +@@ -2210,7 +2191,7 @@ impl Read for Chain { + } + } + +-#[stable(feature = "chain_bufread", since = "1.9.0")] ++#[cfg(feature="collections")] + impl BufRead for Chain { + fn fill_buf(&mut self) -> Result<&[u8]> { + if !self.done_first { +@@ -2235,7 +2216,6 @@ impl BufRead for Chain { + /// Please see the documentation of [`take`] for more details. + /// + /// [`take`]: trait.Read.html#method.take +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Take { + inner: T, +@@ -2270,7 +2250,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "rust1", since = "1.0.0")] + pub fn limit(&self) -> u64 { + self.limit + } +@@ -2298,7 +2277,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "take_set_limit", since = "1.27.0")] + pub fn set_limit(&mut self, limit: u64) { + self.limit = limit; + } +@@ -2323,7 +2301,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "io_take_into_inner", since = "1.15.0")] + pub fn into_inner(self) -> T { + self.inner + } +@@ -2348,7 +2325,6 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_ref(&self) -> &T { + &self.inner + } +@@ -2377,13 +2353,11 @@ impl Take { + /// Ok(()) + /// } + /// ``` +- #[stable(feature = "more_io_inner_methods", since = "1.20.0")] + pub fn get_mut(&mut self) -> &mut T { + &mut self.inner + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Take { + fn read(&mut self, buf: &mut [u8]) -> Result { + // Don't call into inner reader at all at EOF because it may still block +@@ -2401,6 +2375,7 @@ impl Read for Take { + self.inner.initializer() + } + ++ #[cfg(feature="collections")] + fn read_to_end(&mut self, buf: &mut Vec) -> Result { + // Pass in a reservation_size closure that respects the current value + // of limit for each read. If we hit the read limit, this prevents the +@@ -2409,7 +2384,7 @@ impl Read for Take { + } + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl BufRead for Take { + fn fill_buf(&mut self) -> Result<&[u8]> { + // Don't call into inner reader at all at EOF because it may still block +@@ -2436,13 +2411,11 @@ impl BufRead for Take { + /// Please see the documentation of [`bytes`] for more details. + /// + /// [`bytes`]: trait.Read.html#method.bytes +-#[stable(feature = "rust1", since = "1.0.0")] + #[derive(Debug)] + pub struct Bytes { + inner: R, + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Iterator for Bytes { + type Item = Result; + +@@ -2466,14 +2439,14 @@ impl Iterator for Bytes { + /// Please see the documentation of [`split`] for more details. + /// + /// [`split`]: trait.BufRead.html#method.split +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Split { + buf: B, + delim: u8, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Split { + type Item = Result>; + +@@ -2498,13 +2471,13 @@ impl Iterator for Split { + /// Please see the documentation of [`lines`] for more details. + /// + /// [`lines`]: trait.BufRead.html#method.lines +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + #[derive(Debug)] + pub struct Lines { + buf: B, + } + +-#[stable(feature = "rust1", since = "1.0.0")] ++#[cfg(feature="collections")] + impl Iterator for Lines { + type Item = Result; + +diff --git a/prelude.rs b/prelude.rs +index 3baab2b..7d96d23 100644 +--- a/prelude.rs ++++ b/prelude.rs +@@ -8,7 +8,8 @@ + //! use std::io::prelude::*; + //! ``` + +-#![stable(feature = "rust1", since = "1.0.0")] ++pub use super::{Read, Seek, Write}; ++#[cfg(feature="collections")] pub use super::BufRead; + +-#[stable(feature = "rust1", since = "1.0.0")] +-pub use super::{BufRead, Read, Seek, Write}; ++#[cfg(feature="collections")] pub use alloc::boxed::Box; ++#[cfg(feature="collections")] pub use collections::vec::Vec; +diff --git a/util.rs b/util.rs +index b9d5dc2..07d090e 100644 +--- a/util.rs ++++ b/util.rs +@@ -1,8 +1,9 @@ + #![allow(missing_copy_implementations)] + +-use crate::fmt; +-use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; +-use crate::mem::MaybeUninit; ++use core::fmt; ++use crate::io::{self, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write}; ++#[cfg(feature="collections")] use crate::io::BufRead; ++use core::mem::MaybeUninit; + + /// Copies the entire contents of a reader into a writer. + /// +@@ -39,7 +40,6 @@ use crate::mem::MaybeUninit; + /// Ok(()) + /// } + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn copy(reader: &mut R, writer: &mut W) -> io::Result + where + R: Read, +@@ -74,7 +74,6 @@ where + /// the documentation of [`empty()`][`empty`] for more details. + /// + /// [`empty`]: fn.empty.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Empty { + _priv: (), + } +@@ -96,12 +95,10 @@ pub struct Empty { + /// io::empty().read_to_string(&mut buffer).unwrap(); + /// assert!(buffer.is_empty()); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn empty() -> Empty { + Empty { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Empty { + #[inline] + fn read(&mut self, _buf: &mut [u8]) -> io::Result { +@@ -113,7 +110,8 @@ impl Read for Empty { + Initializer::nop() + } + } +-#[stable(feature = "rust1", since = "1.0.0")] ++ ++#[cfg(feature="collections")] + impl BufRead for Empty { + #[inline] + fn fill_buf(&mut self) -> io::Result<&[u8]> { +@@ -123,7 +121,6 @@ impl BufRead for Empty { + fn consume(&mut self, _n: usize) {} + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Empty { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Empty { .. }") +@@ -136,7 +133,6 @@ impl fmt::Debug for Empty { + /// see the documentation of `repeat()` for more details. + /// + /// [repeat]: fn.repeat.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Repeat { + byte: u8, + } +@@ -155,12 +151,10 @@ pub struct Repeat { + /// io::repeat(0b101).read_exact(&mut buffer).unwrap(); + /// assert_eq!(buffer, [0b101, 0b101, 0b101]); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn repeat(byte: u8) -> Repeat { + Repeat { byte } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Read for Repeat { + #[inline] + fn read(&mut self, buf: &mut [u8]) -> io::Result { +@@ -190,7 +184,6 @@ impl Read for Repeat { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Repeat { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Repeat { .. }") +@@ -203,7 +196,6 @@ impl fmt::Debug for Repeat { + /// see the documentation of `sink()` for more details. + /// + /// [sink]: fn.sink.html +-#[stable(feature = "rust1", since = "1.0.0")] + pub struct Sink { + _priv: (), + } +@@ -222,12 +214,10 @@ pub struct Sink { + /// let num_bytes = io::sink().write(&buffer).unwrap(); + /// assert_eq!(num_bytes, 5); + /// ``` +-#[stable(feature = "rust1", since = "1.0.0")] + pub fn sink() -> Sink { + Sink { _priv: () } + } + +-#[stable(feature = "rust1", since = "1.0.0")] + impl Write for Sink { + #[inline] + fn write(&mut self, buf: &[u8]) -> io::Result { +@@ -251,7 +241,6 @@ impl Write for Sink { + } + } + +-#[stable(feature = "std_debug", since = "1.16.0")] + impl fmt::Debug for Sink { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad("Sink { .. }") diff --git a/src/lib.rs b/src/lib.rs index 72c1bb5..d11b916 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -2,10 +2,12 @@ //! This is just a listing of the functionality available in this crate. See //! the [std documentation](https://doc.rust-lang.org/nightly/std/io/index.html) //! for a full description of the functionality. -#![allow(stable_features,unused_features)] +#![allow(stable_features,unused_features,incomplete_features)] #![feature(question_mark,const_fn,copy_from_slice,try_from,str_internals,align_offset, - doc_spotlight,slice_internals)] -#![cfg_attr(any(feature="alloc",feature="collections"),feature(alloc))] + doc_spotlight,slice_internals,maybe_uninit_ref,mem_take,specialization)] +#![cfg_attr(any(feature="alloc",feature="collections"),feature(alloc,allocator_api))] +#![cfg_attr(feature="collections",feature(vec_spare_capacity,maybe_uninit_slice, + new_uninit,debug_non_exhaustive))] #![cfg_attr(pattern_guards,feature(bind_by_move_pattern_guards,nll))] #![cfg_attr(not(no_collections),feature(collections))] #![cfg_attr(non_exhaustive,feature(non_exhaustive))] @@ -32,23 +34,23 @@ pub type ErrorString = &'static str; struct FakeBox(core::marker::PhantomData); #[cfg(not(feature="alloc"))] impl FakeBox { - fn new(val: T) -> T { - val - } + fn new(val: T) -> T { + val + } } // Needed for older compilers, to ignore vec!/format! macros in tests #[cfg(not(feature="collections"))] #[allow(unused)] macro_rules! vec ( - ( $ elem : expr ; $ n : expr ) => { () }; - ( $ ( $ x : expr ) , * ) => { () }; - ( $ ( $ x : expr , ) * ) => { () }; + ( $ elem : expr ; $ n : expr ) => { () }; + ( $ ( $ x : expr ) , * ) => { () }; + ( $ ( $ x : expr , ) * ) => { () }; ); #[cfg(not(feature="collections"))] #[allow(unused)] macro_rules! format { - ( $ ( $ arg : tt ) * ) => { () }; + ( $ ( $ arg : tt ) * ) => { () }; } include!(concat!(env!("OUT_DIR"), "/io.rs"));