Hi all,
NEWS:
I have setup a github for my experiments.
So you can find all my information here:
https://github.com/utessel/mycloud
Most important:
This posting is about how to unbrick a MyCloud without opening it.
At least: Some important steps to do this…
Disclaimer:
1.) It is not a complete walkthrough how to do this.
2.) I cannot (and will not) explain or help how to unbrick your device.
3.) I hope someone else will clean this up, improve it and create something even more useful out of it:
I just wrote down the steps I did, (ok, with a little bit of cleanup already)
If there is a wiki or something like that for this: feel free to use my information.
4.) I will not provide any binaries I created for myself.
My background:
I bought a broken MyCloud (in fact to have a second one, just to be able try this) and started to “unbrick” that, and I was trying it the hard way: Not connecting the disk to anything else.
So in fact my MyCloud was open: This allowed me to use a serial console to watch what is happening. But that is finally not required at all.
The final result works like this:
-
you need a working DHCP server that sends a TFTP Server address: I use dnsmasq for this. (don’t ask me how to configure that!)
-
Setup a tftp folder with two files “startup.sh” and “uImage” (more about these files below)
-
Execute (my) rawping command to send the magic ICMP packet (you find it in my other posting about the serial interface)
-
Power your MyCloud device (I expect you already have a working LAN connection).
-
Wait a bit and you can connect via telnet to your device and you can start to repair it.
So how does this work:
After power on the device starts the first and the second barebox loader.
The second barebox sees the “magic packet” and now tries to download startup.sh from the tftp server:
Mine looks like this:
startup.sh
echo Will boot via tftp
timeout -c 2
addpart /dev/mem 8M@0x3008000(uImage)
tftp uImage /dev/mem.uImage
bootargs="console=ttyS0,115200n8, "
bootargs="$bootargs mac_addr=$eth0.ethaddr panic=3"
bootm /dev/mem.uImage
This will now load the kernel (=uImage) via tftp and start it.
The kernel boots and will use its “initramfs” that I compiled into it:
My “initramfs” contains just the network modules, a busybox installation and a few scripts:
These scripts will start the network, make a dhcp request (again) and finally start telnetd:
Now I can connect via telnet to my box.
The whole procedure does not need anything on the disk at all.
I expect it would work even without having a disk, but I didn’t try that.
I now can mount partitions, communicate via network, whatever busybox allows.
So it should be possible to download new images to the disk etc.
Or simply repair the broken script you have changed?
You now might ask “how can i create that uImage file?”
For that I used two things:
-
The kernel from the GPL package
-
and the busybox sources (I used busybox-1.22.1 I already had from an openwrt installation).
For busybox I used “defconfig”, and changed (via menuconfig) to build it “static” (that is important).
For the kernel I changed (via menuconfig) to use initramfs and added the path to my initramfs.cpio.gz.
(in fact I tried a lot of other changes, but finally was able to remove all of them for this…)
Here is my script I used to compile busybox and the kernel and generating the scripts in the initramfs:
Disclaimer:
I know I don’t have all steps repeatable with this script. As I tried this several times, I know I copied the modules from the _bin folder (created during kernel compile) to the _install folder of busybox once.
Maybe I forgot other steps I did. But I hope someone else can fill this gap.
export ARCH=arm
export CROSS_COMPILE=arm-linux-gnueabi-
cd busybox-1.22.1
make -j8 install
cd _install
mkdir {bin,dev,sbin,etc,proc,sys,lib}
mkdir lib/modules
mkdir dev/pts
mkdir -p usr/share/udhcpc
echo "#!/bin/sh" >init
echo "mount -t proc proc /proc" >>init
echo "mount -t sysfs sysfs /sys" >>init
echo "mount -t devpts none /dev/pts" >>init
echo "echo /sbin/mdev >/proc/sys/kernel/hotplug" >>init
echo "mdev -s" >>init
echo "insmod /lib/modules/3.2.26/pfe.ko lro_mode=1 tx_qos=1 alloc_on_init=1" >>init
echo "ifconfig eth0 up" >>init
echo "udhcpc -b" >>init
echo "telnetd -l/bin/sh" >>init
echo "exec /sbin/init" >>init
chmod +x init
echo "T0:2345:respawn:/sbin/getty -L ttyS0 115200 vt100" >etc/inittab
echo "ttyS0::askfirst:-/bin/sh" >etc/inittab
echo "#!/bin/sh" >usr/share/udhcpc/default.script
echo "case \"\$1\" in" >>usr/share/udhcpc/default.script
echo " renew|bound)" >>usr/share/udhcpc/default.script
echo " /sbin/ifconfig \$interface \$ip \$BROADCAST \$NETMASK" >>usr/share/udhcpc/default.script
echo " ;;" >>usr/share/udhcpc/default.script
echo "esac" >>usr/share/udhcpc/default.script
echo "exit 0" >>usr/share/udhcpc/default.script
chmod +x usr/share/udhcpc/default.script
sudo mknod dev/null c 1 3
sudo mknod dev/tty c 5 0
sudo mknod dev/console c 5 1find . | cpio -H newc -o > ../../initramfs.cpio
cd ../..
cat initramfs.cpio | gzip > initramfs.cpio.gz
cp initramfs.cpio.gz packages/kernel_3.2/
cd packages/kernel_3.2
make uImage
cp _bld/arch/arm/boot/uImage /home/tftp/
Oh:
I used the compiler I got from the ubuntu 14.04 installation (sudo apt-get install gcc-arm-linux-gnueabi),
not the one wd uses.
In fact I think I will now try to setup a clean debian system on my device, as I don’t need all the cloud things…
Ciao,
Baerle