Jeff Griffin

Wake on Lan with IronPython

Posted on April 14, 2011

Since introducing a custom built Media Center PC to my living room configuration back in 2005, the machine filling the role has also become a local storage server of sorts.  The music functions and storage requirements alone make it an appealing location for centralized storage.  Of course it's not always on, nor would we really want it to be, so we would need an easy way to wake it up from workstations, phones, and laptops on the LAN.

Enter Wake-on-Lan.  It wasn't difficult to figure this out. In fact my Xbox, which we were using as an extender in the bedroom, was already using it.  With that already working, there was no configuration to be done on the Media Center PC itself (I'll cover it anyway).  Writing a WOL.exe to form the "Magic Packet" and send it was easy, setting up shortcuts on my wife's and my own systems with the right command arguments to include the port and the Media Center's MAC address was even easier.

In my last post I discussed Windows scripting, and it seemed like something like this was a good candidate for an example.  Plus, back when I wrote that WOL.exe, it seemed a little heavy handed, but I still loved the simplicity of the code itself and wanted to share it.

Set up the Host

As I said, I didn't have to mess with this, but you will need to make sure that your host's network adapter is ready to receive a Wake-on-Lan. Go to device manager, open up your favorite network adapter, and make sure the setting to the right is enabled.

While you're at it, get the MAC address of the adapter.  You can do an "ipconfig /all" in the command prompt and it will be listed as "Physical Address".  Write this down for later.

Some systems will require that you modify settings in the BIOS to support Wake-on-Lan.  I'm not going to cover it, since BIOS menus vary, but this was another thing that I happily didn't need to do.

The Script
Pull out the MAC address you recorded from the host machine and place each hex digit in the byte array, WAKE_MAC_ADDRESS.

import clr
clr.AddReference('System')
clr.AddReference('System.Core')
from System import *
from System.Net.Sockets import *
from System.Net import *
from System.Linq import *

WAKE_MAC_ADDRESS = Array[Byte]([0x0A,0x0D,0x0D,0x04,0x0E,0x55])
PORT = 40000

#fill the first 6 bytes of the packet with 0xFF
magicPacket = Enumerable.Repeat[Byte](0xff, 6);

#repeat the MAC address 16 times
for i in range(16):
magicPacket = Enumerable.Concat(magicPacket, WAKE_MAC_ADDRESS)

#send a UDP boradcast of the magic packet
socket = Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp)
broadcastEndpoint = IPEndPoint(IPAddress.Broadcast, PORT)
socket.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.Broadcast, True)
socket.SendTo(Enumerable.ToArray(magicPacket), broadcastEndpoint)
socket.Close()


Shortcut

What I did at this point was to make a shortcut called "Wake Emcee" (Emcee being the name of my Media Center PC), and pointed it to ScriptShell using the -a option so it silently executes the script and exits.  Shell32.dll has the perfect icon for this.  It will be the default location searched, if you click "Change Icon...".