Please note the implementation below does not work anymore in most cases. Check out the closing note for more info.
Recently there has been quite some attention around, and the security of the WhatsApp application.
Today released a small windows application to change WhatsApp statuses from your desktop.
As I’m not a big fan of the Windows OS (for me), I was curious to take a further look on how the application works – and wanted to find out what the buzz (and assumed insecurity of WhatsApp) was about. This post explains what I did, and what the results are. I’ll leave interpretations and conclusions around WhatsApp security up to the reader, but do feel it’s quite obvious :)

The core of the WhatsApp status changer is a small routine, making an HTTP request to the WhatsApp server, pretending it’s an iPhone client:

private void btnChangeStatus_Click(object sender, EventArgs e)
HttpWebRequest request = (HttpWebRequest) WebRequest.Create("");
request.KeepAlive = false;
request.ProtocolVersion = HttpVersion.Version10;
request.Method = "POST";
request.UserAgent = "User-Agent:WhatsApp/2.6.7 iPhone_OS/5.0.1 Device/Unknown_(iPhone4,1)";
byte[] bytes = Encoding.ASCII.GetBytes("cc=31&me=" + 
               Uri.EscapeDataString(this.txtPhoneNumber.Text) + 
               "&s=" + Uri.EscapeDataString(this.txtNewStatus.Text));
request.ContentType = "application/x-www-form-urlencoded";
request.ContentLength = bytes.Length;
Stream requestStream = request.GetRequestStream();
requestStream.Write(bytes, 0, bytes.Length);
HttpWebResponse response = (HttpWebResponse) request.GetResponse();
MessageBox.Show("Status has been changed to: " + this.txtNewStatus.Text);

Breaking down the code is pretty easy, even with my limited knowledge of .NET code. The call is constructed as a plain HTTP GET request to with three parameters:

  • cc=31
    I’m assuming ‘cc’ stands for ‘country code’, in the application hardcoded to 31, the country code of the Netherlands.

  • me=<phonenumber>
    This is the (encoded) phone number of the recipient (i.e. your number, as you obviously wouldn’t want to change someone else’s status :) )

  • s=<status>
    This is the (encoded) status you want to set.

All parameters should be URL-escaped, to allow the call to go trough.

Obvously this is trivial to replicate. The WhatsApp status changer is not that well-written, and doesn’t contain error handling. This is trivial to add, but the application makes the point.
There is no security whatsoever in the way WhatsApp deals with these calls. I would at least expect some kind of authentication based on a device ID or some other shared secret. This would be my first advice to WhatsApp.

Looking at this, I wonder what the rest of the security is like – but personally I’m less enthousiastic for using WhatsApp for privacy-sensitive communication – and I certainly will trust WhatsApp much less.

If anyone feels like implementing above in some kind of more *nix-friendly library or app, I’d be happy to hear about it. Enjoy, and please use this information responsibly.

Update: Thanks to BlueSky – A quick and easy way to do this from a *nix command shell, assuming you have curl installed:

curl –data-urlencode cc=”31″ –data-urlencode me=”+thephonenumber” –data-urlencode s=”yourstatus” \
     -A “WhatsApp/2.6.7 iPhone_OS/5.0.1 Device/Unknown_(iPhone4,1)-H “Accept: */*” \
     -H “Accept-Language: en-us” -H “Accept-Encoding: gzip, deflate” \
     -L -k -v

Update #2: BlueSky wrote an implementation in PHP – and placed it on pastebin.

Update #3: WhatsApp implemented an IP check – so this doesn’t work as well as it used to. The check entails checking if the update-request is for a WhatsApp account currently signed in, and checks if it is coming from the same IP as the target client is using. This means above could should still work for target WhatsApp users behind the same NAT (for example).