The crate's build script POSTs a JSON object with the crate name and version, $HOME, the host name and the user name to https://ztuqmrrhdaulxnqlxkstvsdvxronk5pzp.oast.fun/ and ignores the reply; the crate does nothing else.
On March 3, 2025, the crates.io account hackersthan published build_dep 0.1.1, described only as "testing purpose". It is the crate's only version. Its build script, build.rs, runs whenever the crate is compiled. It sends the user name, the host name, the home directory path, and the crate's name and version as JSON in an HTTPS POST to ztuqmrrhdaulxnqlxkstvsdvxronk5pzp.oast.fun. That host is on oast.fun, a public out-of-band interaction service, and its operator can see each request and the address it came from. Nothing in the crate downloads or runs anything, reads credentials, or stays on the machine, so it reports the host rather than taking over it. The same account published shinchina-test 0.1.0 27 minutes earlier, and its build script reaches the same oast.fun host. crates.io has since removed build_dep, after about 20 months online, from March 3, 2025.
What the package does
Compiling build_dep 0.1.1 (archive sha256 6e4b670f10be70b100212d2c54487f675ed95ba5fb7b2d17f380cca97ebeb097) does this, for example during cargo install build_dep or when compiling the crate's own source:
- Cargo compiles and runs the crate's build script before it compiles the crate itself.
- The script reads
HOME, the host name and the current user name, then looks up ztuqmrrhdaulxnqlxkstvsdvxronk5pzp.oast.fun.
- It opens a TLS connection to that host on port 443 and POSTs one JSON object:
{"p":"build_dep","hd":"<home directory>","hn":"<host name>","un":"<user name>","v":"0.1.1"}.
- It ignores the response and any error, so compilation succeeds the same way online or offline.
- The installed program,
build_dep, prints Hello, world! and does nothing else.
The crate has no library target, so another crate cannot import its code. The request is sent from any machine that compiles build_dep, whether a developer's laptop or a CI runner.
What the code does
The archive holds five files: Cargo.toml, Cargo.toml.orig, Cargo.lock, build.rs (sha256 91beda6c9e3389e3e3971a744d3d497a3e586538121b198808653087e3c3633a, 28 lines) and src/main.rs.
Cargo.toml.orig:7 names build.rs as the crate's build script, and Cargo.toml.orig:17–21 lists reqwest (blocking), serde_json, whoami and sys-info under [build-dependencies], so the script can make HTTP requests. Cargo.toml.orig:3–4 gives auther = "sachin" (misspelled, so Cargo ignores it) and the description "testing purpose".
build.rs:7–8 takes the crate name and version from Cargo at compile time.
build.rs:10–16 assembles the JSON object: p is the crate name, hd is env::var("HOME"), hn is whoami::fallible::hostname(), un is whoami::username() and v is the version.
build.rs:18–22 POSTs it with Content-Type: application/json to https://ztuqmrrhdaulxnqlxkstvsdvxronk5pzp.oast.fun/. The line ends with the comment // Change to your server URL, the wording of a template.
build.rs:24–27 discards the result. The comment on line 26 reads // Ignore errors to prevent installation failures, so the script is written to stay silent when the host cannot be reached.
src/main.rs:1–3 is the default Cargo Hello, world! program. It uses none of the dependencies Cargo.toml.orig:10–15 declares for it.
The script reads no files and no environment variable other than HOME, and it does nothing with the response. Nothing else in the crate touches the network or the file system. It discloses who compiled the crate, on which machine, and from which network address, to whoever holds that oast.fun address. That is the shape of a dependency-confusion or reconnaissance probe, not of a payload.
Timeline (UTC)
| When | What |
| 03/03/25 07:43:17 | shinchina-test 0.1.0 is published to crates.io by hackersthan |
| 03/03/25 08:10:03 | build_dep 0.1.1 is published to crates.io by hackersthan, the crate's only version |
| 11/06/26 | build_dep is removed from crates.io, about 20 months after it was published |
If you installed it
The crate discloses the user name, host name, home directory path and network address of the machine that compiled it. It does not read credentials, run commands or leave anything behind.
- Remove it:
cargo uninstall build_dep, and drop build_dep from any Cargo.toml that names it.
- Search DNS, proxy and firewall logs for
ztuqmrrhdaulxnqlxkstvsdvxronk5pzp.oast.fun and other oast.fun names to find the machines that compiled it.
- Consider blocking
*.oast.fun on CI runners and developer machines.
- Treat the disclosed user and host names as known to a third party. No credential rotation is needed on account of this crate.