WOL + Ping

Just starting out? Need help? Post your questions and find answers here.
User avatar
blueznl
PureBasic Expert
PureBasic Expert
Posts: 6166
Joined: Sat May 17, 2003 11:31 am
Contact:

WOL + Ping

Post by blueznl »

Actually, I'd rather simply download this somewhere and be done with it 8) but I haven't found it.

I need this little tool to aid (mis)behaving HTPC's and the like. When they are switched on, I need them to send a wakeup call to my homeserver, but I need that to work only if there is a network up and running (ie. if there's no network they have to wait).

It would look something like this:

1. check if the network is up (probably simply checking for an allocated IP address would do, ie. once 0.0.0.0 has been replaced by something like 192.168.0.110 or something similar), this I know how to do (would be interesting to see if there's something to check if a wifi link is up, but that isn't required)

2. once up, send a WOL to a specific MAC address, if anyone would have a WOL sample code, I'd appreciate it (especially a PureBasic working one :twisted: )

3. ping the intended server, until it replies

Why this approach? Take a laptop that's abuses as HTPC, it first builds up a wifi link, and when that link is up the laptop gets it's network assigned IP address (DHCP, though I noticed that with some wifi adapters even a fixed IP is reported as 0.0.0.0 until the wifi link is connected). However, even if there is a local valid IP address, it sometimes takes another few seconds before you actually can send out a WOL or PING a server, so I guess I would do an intermediate WOL then PING then WOL then PING etc. until the server replies.

Now, put the above on-screen in a single program with a large window with a busy indicator, and life's suddenly good for the poort htpc crowd that uses a power saving server :lol:

I've looked around but couldn't find such an all in one tool, which is weird, but hey, if one can't find it, then it's time to make it.

It's probably doable with scripts / batch files etc. but it all gets so messy that way... Suggestions / solutions / links / samples / help anyone?
( PB6.00 LTS Win11 x64 Asrock AB350 Pro4 Ryzen 5 3600 32GB GTX1060 6GB)
( The path to enlightenment and the PureBasic Survival Guide right here... )
User avatar
JHPJHP
Addict
Addict
Posts: 2251
Joined: Sat Oct 09, 2010 3:47 am

Re: WOL + Ping

Post by JHPJHP »

These looked interesting:

viewtopic.php?p=221986

http://purebasic.info/phpBB2/viewtopic.php?t=1311

Also a nice little Ping script, found near the end of the following thread (Page 1), posted by Freak (modified for Unicode on Page 2):

http://www.forums.purebasic.com/english ... 13&t=24174

If you're not investing in yourself, you're falling behind.

My PureBasic StuffFREE STUFF, Scripts & Programs.
My PureBasic Forum ➤ Questions, Requests & Comments.
User avatar
blueznl
PureBasic Expert
PureBasic Expert
Posts: 6166
Joined: Sat May 17, 2003 11:31 am
Contact:

Re: WOL + Ping

Post by blueznl »

... except for my russian :lol:

But thanks, I think I'm now able to cook up something. When done I'll put the code in here, as I usually do. It just might help someone...
( PB6.00 LTS Win11 x64 Asrock AB350 Pro4 Ryzen 5 3600 32GB GTX1060 6GB)
( The path to enlightenment and the PureBasic Survival Guide right here... )
User avatar
blueznl
PureBasic Expert
PureBasic Expert
Posts: 6166
Joined: Sat May 17, 2003 11:31 am
Contact:

Re: WOL + Ping

Post by blueznl »

Code: Select all

Procedure.i x_pokehex(addr.i,s.s)                                    ; write a hex sequence to memory
  Protected l.i, n.i, p.i, x.s, v.i
  ;
  l = Len(s)
  p = 0
  ;
  While n+1 < l
    n = n+1
    x = Mid(s,n,1)
    If ( x >= "0" And x <= "9" ) Or ( x >= "A" And x <= "F" ) Or ( x >= "a" And x <= "f" )
      x = Mid(s,n+1,1)
      If ( x >= "0" And x <= "9" ) Or ( x >= "A" And x <= "F" ) Or ( x >= "a" And x <= "f" )
        v = Val("$"+Mid(s,n,2))
        n = n+1
        PokeB(addr+p,v)
        p = p+1
      EndIf
    EndIf
  Wend
  ;
  ProcedureReturn p
EndProcedure

Procedure.i x_ping(ipaddress.s, timeout.i=255)                                               ; send imcp echo message ie. ping ip address
  Protected inetaddress.i, file_h.i, message.s{20}
  ;
  ; *** send imcp echo message ie. ping ip address
  ;
  ; notes:
  ;
  ; - based on code by freak and jhpjhp
  ;
  x_pokes(@message,"ECHO"+Hex(Random($FFFFFF)),10,#PB_Ascii)
  ;
  If CountString(ipaddress,".") = 3
    inetaddress = MakeIPAddress(Val(StringField(ipaddress,1,".")),Val(StringField(ipaddress,2,".")),Val(StringField(ipaddress,3,".")),Val(StringField(ipaddress,4,".")))
  EndIf
  file_h = IcmpCreateFile_()
  IcmpSendEcho_(file_h, inetaddress, @message, 10, 0, @x_echo, SizeOf(x_echo), timeout)
  IcmpCloseHandle_(file_h)
  ;
  ;
  If x_echo\reply\status Or x_peeks(@message,10,#PB_Ascii) <> x_peeks(@x_echo\buffer,10,#PB_Ascii)
    ProcedureReturn -1
  Else
    ProcedureReturn x_echo\reply\RoundTripTime
  EndIf
  ;
EndProcedure

Procedure.i x_wol(mac.s, ip.s="255.255.255.255", port.l=0)                                   ; send magic packet (wakeonlan)
  Protected p.i, n.i
  Protected bip.l, bport.w, socket.l, keepalive.b, servermode.l, sockaddr.SOCKADDR_IN, send.i
  Protected Dim magicpacket.b(102)
  ;
  ; *** send a magic packet to another computer
  ;
  ; notes
  ;
  ; - need to call either InitNetwork() or x_ws_start() before calling this procedure
  ; - specifying port and IP might be useful on WAN's but for LAN's just broadcast to 255.255.255.255:0
  ; 
  ; build the magic packet
  ;
  p = @magicpacket(0)
  ;
  ; header is 16 bytes $FF
  ;
  x_pokehex(p, "$ FF FF FF FF FF FF")
  ;
  ; followed by 16x mac address
  ;
  For n = 1 To 16
    x_pokehex(p+n*6,mac)
  Next n
  ;
  ; open a socket and send the message
  ;
  x_retval = 0
  ;
  socket = SOCKET_(#AF_INET, #SOCK_DGRAM, #IPPROTO_UDP)
  If socket
    keepalive = 1
    If setsockopt_(socket, #SOL_SOCKET, #SO_BROADCAST, @keepalive, 1) = 0
      sockaddr.SOCKADDR_IN
      sockaddr\sin_family = #AF_INET
      sockaddr\sin_port   = htons_(port)
      sockaddr\sin_addr   = inet_addr_(ip)
      servermode          = 0
      If ioctlsocket_(socket,#FIONBIO,@servermode) = 0
        send = sendto_(socket, p, 102, 0, @sockaddr, 16)
        If send=102 And WSAGetLastError_()=0
          x_retval = 1
        EndIf
      EndIf
    EndIf
    closesocket_(socket)
  EndIf
  ;
  ProcedureReturn x_retval
EndProcedure
( PB6.00 LTS Win11 x64 Asrock AB350 Pro4 Ryzen 5 3600 32GB GTX1060 6GB)
( The path to enlightenment and the PureBasic Survival Guide right here... )
Post Reply