Close

[OLD REPOST] First attempt at "desciphering" the UDP comms

A project log for Controlling a JJRC H37 Elfie quad from a PC

The JJRC Elfie Quadcopter comes with an Android/iOS app to control it from the phone. Can we control it from our own software?

adria.junyent-ferreadria.junyent-ferre 02/20/2017 at 11:190 Comments

NOTE: this text was originally included in the description of the project and perhaps should have been a log update instead. I reposted it here even though it is outdated and the problems described here were solved later on.

I've only played with this for one or two hours and I haven't been able to decode the 8 byte message; however, a few bits seem to change when one enables things such as the "altitude hold" or the "headless mode" and a few of the bytes also change whenever the control levers in the screen (thrust, yaw, etc) move.

I tried following my normal startup sequence in the quadcopter, where I first enable the altitude hold, then I enable the on-screen controllers and then I "arm" the propellers by pressing the up arrow button in the screen. This leaves the quadcopter ready to take off. This sequence generates the following messages:

66 80 80 01 80 00 81 99 "idle state" (on-screen controllers are enabled but the quad is idle and the altitude hold is disabled)

66 80 80 80 80 00 00 99 "idle state with altitude hold" (the previous message changes to this message as soon as the altitude hold is enabled)

66 80 80 80 80 01 01 99 "arm propellers" (the previous message becomes this when the altitude hold is on, the on-screen controllers are on and the "up arrow" button is pressed in order to arm the motors". The message is sent some 20-22 times -for about a second-).

66 80 80 80 80 04 04 99 "emergency stop" (this is the message that is sent starting from the idle state with altitude hold as soon as the emergency stop button is pressed. The message is sent some 20-22 times -for about a second-).

Using the information described above, I put together a small Python script that opens a UDP connection to port 8859 in the quadcopter and writes the series of commands that I describe above. The sequence sends a message every 50 miliseconds and leaves some of the messages for a certain amount of time, replicating more or less the sequence I follow when I want to get the quadcopter to be ready to fly.

If you want to give the demo a try. Take your laptop, make sure you don't have any browser/software running that is internet-hungry and will flood the quadcopter with useless requests, connect your laptop to the wifi of the quadcopter and run the application doing "python demo.py". What you should see is the quadcopter will arm the motors and make the propellers speed up some 10 seconds after starting the app. The propellers will spin for a few seconds and then the program will turn them off and disconnect.

THE DEMO CODE

import socket
from time import sleep

# The IP of the quadcopter plus the UDP port it listens to for control commands
IPADDR = '172.16.10.1'
PORTNUM = 8895
 
# "idle" message, this is the first message the app sends to the quadcopter when you enable the controls
PIDLE = '6680800180008199'.decode('hex') 
# "altitude hold" this is what the app starts sending to the quadcopter once you enable the altitude hold
PHOLD = '6680808080000099'.decode('hex')
# "arm" this is what the app sends to the quadcopter when you press the "up" arrow that make the motors start to spin before taking off
PSPIN = '6680808080010199'.decode('hex')
# this is the message the app sends to the quadcopter when you press the "emergency stop" button
PSTOP = '6680808080040499'.decode('hex')
 
# initialize a socket
# SOCK_DGRAM specifies that this is UDP
s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM, 0)
 
# connect the socket
s.connect((IPADDR, PORTNUM))
 
# send a series of commands
for n in range(0,100): # send the idle command for some 5 seconds
    s.send(PIDLE)
    sleep(0.05) # the app sends a packet of 8 bytes every 50 miliseconds

for n in range(0,100): # send the idle + altitude hold command for some 5 seconds
    s.send(PHOLD)
    sleep(0.05)

for n in range(0,21): # send the "arm" command for 1 second (this is what the app seems to do when you press the up arrow to arm the quadcopter
    s.send(PSPIN)
    sleep(0.05)

for n in range(0,100): # send the idle + altitude hold command for some 5 seconds
    s.send(PHOLD)
    sleep(0.05)

for n in range(0,21): # send the "emergency stop" command for 1 second
    s.send(PSTOP)
    sleep(0.05)

for n in range(0,200): # send the idle + altitude hold for some 5 seconds
    s.send(PHOLD)
    sleep(0.05)

# close the socket
s.close()

Discussions