├── LICENSE.md ├── Protocol ├── .gitignore └── latex │ ├── arcommands.tex │ ├── ardiscovery.tex │ ├── arnetwork.tex │ ├── arnetworkal.tex │ ├── arstream.tex │ ├── commands.tex │ ├── cover.pdf │ ├── logo.png │ ├── main.tex │ └── purpose.tex ├── README.md └── SkyController ├── .gitignore └── latex ├── advanced.tex ├── changed.tex ├── commands.tex ├── connection.tex ├── cover.pdf ├── generic.tex ├── logo.png ├── main.tex ├── new.tex ├── purpose.tex ├── same.tex └── setup.tex /LICENSE.md: -------------------------------------------------------------------------------- 1 | Copyright (C) 2014 Parrot SA 2 | 3 | Redistribution and use in source and binary forms, with or without 4 | modification, are permitted provided that the following conditions 5 | are met: 6 | * Redistributions of source code must retain the above copyright 7 | notice, this list of conditions and the following disclaimer. 8 | * Redistributions in binary form must reproduce the above copyright 9 | notice, this list of conditions and the following disclaimer in 10 | the documentation and/or other materials provided with the 11 | distribution. 12 | * Neither the name of Parrot nor the names 13 | of its contributors may be used to endorse or promote products 14 | derived from this software without specific prior written 15 | permission. 16 | 17 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 18 | "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 19 | LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS 20 | FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE 21 | COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, 22 | INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, 23 | BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS 24 | OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED 25 | AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, 26 | OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT 27 | OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 28 | SUCH DAMAGE. -------------------------------------------------------------------------------- /Protocol/.gitignore: -------------------------------------------------------------------------------- 1 | *.toc 2 | latex/main.pdf 3 | *.log 4 | *.out 5 | *.aux 6 | *~ 7 | 8 | _region_.tex 9 | -------------------------------------------------------------------------------- /Protocol/latex/arcommands.tex: -------------------------------------------------------------------------------- 1 | \section{ARCommands protocol} 2 | 3 | The \ARCode{ARCommand} library is a simple codec for sending binary data on the network. 4 | 5 | \subsection{Command identifier} 6 | 7 | The command is identified by its first 4 bytes: 8 | \begin{itemize} 9 | \item{Project or Feature ID (1 byte)} 10 | \item{Class ID in the project/feature (1 byte)} 11 | \item{Command ID in the class (2 bytes)} 12 | \end{itemize} 13 | 14 | In this document, commands are noted in the \ARCode{Project.Class.Command} notation. For example, the \ARCode{PCMD} command, in class \ARCode{Piloting} for project \ARCode{ARDrone3} is \ARCode{ARDrone3.Piloting.PCMD}. 15 | 16 | \subsection{Command arguments} 17 | 18 | The command arguments are directly packed after the command ID. Multi-bytes values are sent in little endian to avoid bytes swap in the product. 19 | 20 | Here is a list of the supported argument types: 21 | \begin{table}[h] 22 | \centering 23 | \begin{tabular}{|c|c|c|} 24 | \hline 25 | Type & Size (bytes) & Description \\ 26 | \hline 27 | \hline 28 | u8 & 1 & unsigned 8bit value \\ 29 | i8 & 1 & signed 8bit value \\ 30 | \hline 31 | u16 & 2 & unsigned 16bit value \\ 32 | i16 & 2 & signed 16bit value \\ 33 | \hline 34 | u32 & 4 & unsigned 32bit value \\ 35 | i32 & 4 & signed 32bit value \\ 36 | \hline 37 | u64 & 8 & unsigned 64bit value \\ 38 | i64 & 8 & signed 64bit value \\ 39 | \hline 40 | float & 4 & IEEE-754 single precision \\ 41 | double & 8 & IEEE-754 double precision \\ 42 | \hline 43 | string & * & Null terminated string (C-String) \\ 44 | & & (Variable size)\\ 45 | \hline 46 | enum & 4 & Per command defined enum \\ 47 | & & Coded as i32 on network \\ 48 | \hline 49 | \end{tabular} 50 | \caption{Supported types for \ARCode{ARCommand} arguments} 51 | \end{table} 52 | 53 | \subsection{Commands definition} 54 | 55 | Commands are defined in xml files. All the source code of the \ARCode{ARCommands} library is generated from these files. 56 | 57 | The current xml files can be found in the \href{https://github.com/Parrot-Developers/libARCommands/tree/master/Xml}{\ARCode{/libARCommands/Xml}} directory. 58 | 59 | In this directory, each \ARCode{.xml} file correspond to a project or a feature. Each product only understand a given list of features. Here is a list of features implemented per product: 60 | 61 | \begin{table}[h] 62 | \centering 63 | \begin{tabular}{|c|c|} 64 | \hline 65 | Product & Features \\ 66 | \hline 67 | \hline 68 | Bebop Drone & ARDrone3, Common \\ 69 | \hline 70 | Jumping Sumo & JumpingSumo, Common \\ 71 | \hline 72 | Rolling Spider & MiniDrone, Common \\ 73 | \hline 74 | SkyController & SkyController \\ 75 | \hline 76 | Airborne Night & MiniDrone, Common \\ 77 | \hline 78 | Airborne Cargo & MiniDrone, Common \\ 79 | \hline 80 | Hydrofoil & MiniDrone, Common \\ 81 | \hline 82 | Jumping Night & JumpingSumo, Common \\ 83 | \hline 84 | Jumping Race & JumpingSumo, Common \\ 85 | \hline 86 | \end{tabular} 87 | \caption{Features implemented by each product} 88 | \end{table} 89 | 90 | Note that implementing a features means that at least a subset of the feature is useful for the product, not that all commands in the feature are actually implemented! 91 | 92 | Also note that the \ARCode{xxx_debug.xml} files contain debug commands that should be avoided. These commands can change from one version to another without notice, and can have unwanted behavior. 93 | 94 | \subsubsection{The SkyController case} 95 | 96 | The SkyController implements its own set of commands, even for common ones, as it can be connected to another device. When a SkyController is connected to a Bebop Drone, it will forward all \ARCode{ARDrone3.X.Y} and \ARCode{Common.Z.W} commands to the Bebop Drone, and will forward to the controller all the data coming from the Bebop (including the \ARCode{ARStream} data. 97 | 98 | \subsection{Command attributes} 99 | 100 | While not tied to the \ARCode{ARCommand} codec, certain commands can have other xml attributes, namely \ARCode{buffer}, \ARCode{timeout} and \ARCode{listtype}. These attributes are given as hints for an implementer on how the command is intended to be used. 101 | 102 | \subsubsection{buffer} 103 | 104 | The value of this attribute can be either \ARCode{NON_ACK}, \ARCode{ACK} or \ARCode{HIGH_PRIO}, defaulting to \ARCode{ACK} if not given. It gives a hint about the destination buffer for the command. 105 | 106 | For the Bebop Drone, the \ARCode{NON_ACK} buffers are 10 (c2d) and 127 (d2c), the \ARCode{ACK} buffers are 11 (c2d) and 126 (d2c), and the \ARCode{HIGH_PRIO} buffer is the 12 (c2d). 107 | 108 | This is only a hint, and the product will decode any \ARCode{ARCommand} on any \ARCode{ARNetwork} buffer, as long as the buffer is not used for \ARCode{ARStream}. 109 | 110 | \subsubsection{timeout} 111 | 112 | The value of this attribute can be either \ARCode{POP}, \ARCode{RETRY} or \ARCode{FLUSH}, defaulting to \ARCode{POP} if not given. 113 | 114 | For acknowledged data, if a timeout happens (after the retries from \ARCode{ARNetwork}), there is three possible answers: 115 | \begin{itemize} 116 | \item{POP: Pop the data from the fifo, and continue with the next data (default).} 117 | \item{RETRY: Retry the data. This leads to infinite retries of the current data.} 118 | \item{FLUSH: Flush the entire \ARCode{ARNetwork} buffer. This can be useful if the next data depends on the current one.} 119 | \end{itemize} 120 | 121 | This information has no effect on non acknowledged data. 122 | 123 | \subsubsection{listtype} 124 | 125 | The value of this attribute can be either \ARCode{NONE}, \ARCode{LIST} or \ARCode{MAP}, defaulting to \ARCode{NONE} if not given. 126 | 127 | \ARCode{LIST} commands are sent multiple times, and a list of all the received value should be created. The \ARCode{ARController} library uses a hash map with a locally generated integer key to emulate this. 128 | 129 | \ARCode{MAP} commands are sent multiple times, and their first argument should be used as a key in a map of received values. 130 | 131 | In both cases, clearing the map/list before requesting the data is the responsibility of the receiver, unless stated otherwise in a specific command implementation. 132 | 133 | \subsection{Commands list} 134 | 135 | Listing all the commands in this document would be too long. The format used in the \ARCode{.xml} files is designed to be human readable, with inline comments about every commands and arguments. 136 | 137 | Some of the important commands are listed below. 138 | 139 | \subsubsection{\ARCode{Common.Settings.AllSettings} \&\\\ARCode{Common.Common.AllStates}} 140 | 141 | Normally, the product will send state and settings updates on the go. To synchronize them, you will have to request a full snapshot of the settings and the states of the product during the initialization. 142 | 143 | When receiving these commands, the product will send all its settings (or states), then it will send a final command, saying that all the settings or state were sent. 144 | 145 | The SkyController uses the \ARCode{SkyController.Settings.AllSettings} and \ARCode{SkyController.Common.AllStates} commands instead. 146 | 147 | \begin{table}[h] 148 | \centering 149 | \resizebox{\textwidth}{!}{% 150 | \begin{tabular}{|c|c|} 151 | \hline 152 | Request & Final answer \\ 153 | \hline 154 | \hline 155 | \ARCode{Common.Settings.AllSettings} & \ARCode{Common.SettingsState.AllSettingsChanged} \\ 156 | \hline 157 | \ARCode{Common.Common.AllStates} & \ARCode{Common.CommonState.AllStatesChanged} \\ 158 | \hline 159 | \hline 160 | \ARCode{SkyController.Settings.AllSettings} & \ARCode{SkyController.SettingsState.AllSettingsChanged} \\ 161 | \hline 162 | \ARCode{SkyController.Common.AllStates} & \ARCode{SkyController.CommonState.AllStatesChanged} \\ 163 | \hline 164 | \end{tabular} 165 | } 166 | \caption{Final command for each Settings/State request} 167 | \end{table} 168 | 169 | \subsubsection{\ARCode{Common.Common.CurrentDate} \&\\\ARCode{Common.Common.CurrentTime}} 170 | 171 | These commands set the date/time on the product, which in turn is set into the media and PUD (for \ARCode{ARDrone Academy} files). 172 | 173 | The argument to these commands is an \href{https://en.wikipedia.org/wiki/ISO_8601}{ISO-8601} formatted string, with the following format: 174 | \begin{itemize} 175 | \item{\ARCode{"yyyy-MM-dd"} for \ARCode{Common.Common.CurrentDate}. Ex: \ARCode{2015-08-27}.} 176 | \item{\ARCode{"'T'HHmmssZZZ"} for \ARCode{Common.Common.CurrentTime}. Ex: \ARCode{T101527+0200}.} 177 | \end{itemize} 178 | 179 | For compatibility purposes, you should always sent both commands to the product, not just the \ARCode{Common.Common.CurrentDate} one. The order is irrelevant on newer firmwares, but older ones need the \ARCode{Common.Common.CurrentTime} to be sent after. 180 | 181 | Note that you should generate both strings from a single time-stamp to avoid any loop error at midnight. 182 | 183 | \subsubsection{\ARCode{ARDrone3.MediaStreaming.VideoEnable} \&\\\ARCode{JumpingSumo.MediaStreaming.VideoEnable}} 184 | 185 | These commands will enable or disable the video streaming from the product. When connecting, the streaming is disabled (which lets a high bandwidth to transfer all the data needed by the \ARCode{Common.Settings.AllSettings} and \ARCode{Common.Common.AllStates} commands). You should enable the video only when needed (when you actually display it !). 186 | 187 | In FreeFlight, the video is also disabled in the following cases: 188 | \begin{itemize} 189 | \item{When the user browses the internal memory of the drone.} 190 | \item{When the user downloads media from the drone.} 191 | \item{When the user sends an update file to the drone.} 192 | \end{itemize} 193 | 194 | 195 | \subsection{Using the ARCommandsParser to generate your own code} 196 | 197 | The code generator is split into a parser, and a generator part. The parser is written in Python, and can be found in the \ARCode{ARSDKBuildUtils} repository: 198 | \ARFile{ARSDKBuildUtils}{Utils/Python/ARCommandsParser.py} 199 | 200 | It defines a \ARCode{parseAllProjects} function, which takes 4 arguments: 201 | \begin{itemize} 202 | \item{projects: A list of strings, list of the projects to parse. If this list contains the ``all'' string, then all projects are parsed, regardless of the content of the other elements.} 203 | \item{pathToARCommands: The path to the \ARCode{ARCommands} library root (not the \ARCode{Xml} directory !)} 204 | \item{genDebug: if True, then the \ARCode{xxx_debug.xml} files are also parsed. Defaults to False. Should not be used} 205 | \item{mergeDebugProjectsInReleaseProjetcs: if True, then the debug commands will be merged with the release commands in single projects instead of being in separated debug projects. Defaults to False. Should not be used} 206 | \end{itemize} 207 | 208 | And returns a list of \ARCode{ARProject} objects. This class (and all other internally used class) are fairly straightforward to understand, and thus are not described in depth here. 209 | 210 | A simple example of iterating on all commands can be seen at lines 519-554 of \ARFile{libARCommands}{Xml/generateLibARCommands.py} 211 | 212 | 213 | %%% Local Variables: 214 | %%% mode: latex 215 | %%% TeX-master: "main" 216 | %%% End: 217 | -------------------------------------------------------------------------------- /Protocol/latex/ardiscovery.tex: -------------------------------------------------------------------------------- 1 | \section{ARDiscovery protocol} 2 | 3 | The \ARCode{ARDiscovery} library is separated in two parts: Discovery, and Connection. The Discovery part is in charge of discovering the devices on the network (for Wifi products) or nearby (for BLE Products), while the Connection part is responsible for negotiating the connection parameters (which are used by the \ARCode{ARNetworkAL} library, among others) 4 | 5 | \subsection{Discovery} 6 | 7 | \subsubsection{Wifi} 8 | 9 | The ARSDK Wifi Products use the \href{https://en.wikipedia.org/wiki/Multicast_DNS}{mDNS} protocol to advertise themselves on the wifi network. You can use any compatible implementation (Apple Bonjour, Avahi, Android NSDManager...) to discover the products. 10 | 11 | The service types for the different products are: 12 | 13 | \begin{table}[h] 14 | \centering 15 | \begin{tabular}{|c|c|} 16 | \hline 17 | Product Name & Service Type \\ 18 | \hline 19 | \hline 20 | Bebop Drone & \ARCode{._arsdk-0901._udp} \\ 21 | \hline 22 | Jumping Sumo & \ARCode{._arsdk-0902._udp} \\ 23 | \hline 24 | SkyController & \ARCode{._arsdk-0903._udp} \\ 25 | \hline 26 | Jumping Night & \ARCode{._arsdk-0905._udp} \\ 27 | \hline 28 | Jumping Race & \ARCode{._arsdk-0906._udp} \\ 29 | \hline 30 | \end{tabular} 31 | \caption{mDNS Service type for the Wifi Products} 32 | \end{table} 33 | 34 | These identifiers can be found in the \\ 35 | \ARFile{libARDiscovery}{Sources/ARDISCOVERY_Discovery.c} file. 36 | 37 | 38 | You can find the following information from the mDNS Service: 39 | \begin{table}[h] 40 | \centering 41 | \resizebox{\textwidth}{!}{% 42 | \begin{tabular}{|c|c|c|} 43 | \hline 44 | Information & Source & Description \\ 45 | \hline 46 | \hline 47 | Name & Service Name & Display name of the product \\ 48 | \hline 49 | IP & Service resolution & IP address of the product \\ 50 | \hline 51 | Port & Service port & Discovery Connection port \\ 52 | \hline 53 | Extras & Service TxtData & A json string containing extra information \\ 54 | & & (currently contains the product serial number) \\ 55 | \hline 56 | \end{tabular} 57 | } 58 | \caption{Information available in the mDNS service} 59 | \end{table} 60 | 61 | \newpage 62 | 63 | \subsubsection{BLE} 64 | 65 | To identify ARSDK BLE Products, you need to get the product Advertising Data. You can use any BLE-Compliant implementation to do this (bluez, Apple CoreBluetooth, Android BluetoothAdapter...). 66 | 67 | 68 | In the manufacturer specific data part of the advertising data, the first 6 bytes should be the following: 69 | \begin{itemize} 70 | \item{Vendor ID (2 bytes) : \ARCode{0x0043} (Parrot Bluetooth ID)} 71 | \item{USB Vendor ID (2 bytes) : \ARCode{0x19cf} (Parrot USB ID)} 72 | \item{USB Product ID (2 bytes) : Depends on product} 73 | \end{itemize} 74 | 75 | \begin{table}[h] 76 | \centering 77 | \begin{tabular}{|c|c|} 78 | \hline 79 | Product Name & USB Product ID \\ 80 | \hline 81 | \hline 82 | Rolling Spider & \ARCode{0x0900} \\ 83 | \hline 84 | Airborne Night & \ARCode{0x0907} \\ 85 | \hline 86 | Airborne Cargo & \ARCode{0x0909} \\ 87 | \hline 88 | Hydrofoil & \ARCode{0x090a} \\ 89 | \hline 90 | \end{tabular} 91 | \caption{USB Product IDs of BLE Products} 92 | \end{table} 93 | 94 | These identifiers can be found in the \\ 95 | \ARFile{libARDiscovery}{Sources/ARDISCOVERY_Discovery.c} file. 96 | 97 | \newpage 98 | 99 | \subsection{Connection} 100 | 101 | \subsubsection{Wifi} 102 | 103 | For wifi products, further negotiation is needed: this is done over a TCP socket, using the mDNS Service port. 104 | 105 | To negotiate the connection, connect a socket to this TCP port, and send a JSON string containing the following information: 106 | \begin{table}[h] 107 | \centering 108 | \resizebox{\textwidth}{!}{% 109 | \begin{tabular}{|c|c|c|} 110 | \hline 111 | Key & Mandatory & Description \\ 112 | \hline 113 | \hline 114 | \ARCode{d2c_port} & Yes & The UDP port you will use to read data \\ 115 | \hline 116 | \ARCode{controller_type} & Yes & The type of the controller \\ 117 | & & (e.g. ``Phone'', ``Tablet''...) \\ 118 | \hline 119 | \ARCode{controller_name} & Yes & The name of the controller \\ 120 | & & (e.g. Application name) \\ 121 | \hline 122 | \ARCode{device_id} & No & The product serial number \\ 123 | \hline 124 | \end{tabular} 125 | } 126 | \caption{Available keys for connection JSON} 127 | \end{table} 128 | 129 | Here is an example of a valid connection JSON string:\\ 130 | \texttt{\{ "d2c\_port":43210, "controller\_type":"Phone", \\ 131 | "controller\_name":"com.example.arsdkapp" \}} 132 | 133 | 134 | The \ARCode{"device_id"} field is useful when reconnecting to a product: If a product receives a connection request with the \ARCode{"device_id"} field, the connection will only be accepted if it matches the product serial number. 135 | 136 | \newpage 137 | 138 | The device will answer a connection request with another JSON string sent on the same TCP socket. This response JSON string can contain the following information: 139 | 140 | \begin{table}[h] 141 | \centering 142 | \resizebox{\textwidth}{!}{% 143 | \begin{tabular}{|c|c|c|} 144 | \hline 145 | Key & Mandatory & Description \\ 146 | \hline 147 | \hline 148 | \ARCode{status} & Yes & If different from 0, it means that the \\ 149 | & & connection is refused (see below) \\ 150 | \hline 151 | \ARCode{c2d_port} & Yes & The UDP port you will send data to \\ 152 | & & (If the connection is refused, this value will be 0) \\ 153 | \hline 154 | \ARCode{arstream_fragment} & No & The size of \ARCode{ARStream} fragments \\ 155 | \ARCode{_size} & & \\ 156 | \hline 157 | \ARCode{arstream_fragment} & No & The maximum number of \ARCode{ARStream} fragments \\ 158 | \ARCode{_maximum_number} & & per video frame. \\ 159 | \hline 160 | \ARCode{arstream_max_} & No & The maximum time between ARStream ACKs \\ 161 | \ARCode{ack_interval} & & \\ 162 | \hline 163 | \ARCode{c2d_update_port} & Yes & The FTP port for updating the product \\ 164 | \hline 165 | \ARCode{c2d_user_port} & No & Another FTP port for other uses \\ 166 | \hline 167 | \ARCode{skycontroller} & SC only & The SkyController version \\ 168 | \ARCode{_version} & & \\ 169 | \hline 170 | \end{tabular} 171 | } 172 | \caption{Available keys for connection answer JSON} 173 | \end{table} 174 | 175 | 176 | Here is an example of a valid connection answer JSON string:\\ 177 | \texttt{\{ "status":0, "c2d\_port":54321, \\ 178 | "arstream\_fragment\_size":65000, \\ 179 | "arstream\_fragment\_maximum\_number":4, \\ 180 | "arstream\_max\_ack\_interval":-1, "c2d\_update\_port":51, \\ 181 | "c2d\_user\_port":61 \}} 182 | 183 | If the \ARCode{status} field is not 0, then it is an \ARCode{eARDISCOVERY_ERROR} enum value. These values can be found in the\\ 184 | \ARFile{libARDiscovery}{Includes/libARDiscovery/ARDISCOVERY_Error.h} file. 185 | 186 | \subsubsection{BLE} 187 | 188 | There is no Connection part for BLE products. Just use your BLE adapter methods to connect to the device. Product pairing is not required for BLE connectivity. 189 | 190 | %%% Local Variables: 191 | %%% mode: latex 192 | %%% TeX-master: "main" 193 | %%% End: 194 | -------------------------------------------------------------------------------- /Protocol/latex/arnetwork.tex: -------------------------------------------------------------------------------- 1 | \section{ARNetwork protocol} 2 | 3 | Each product has its own \ARCode{ARNetwork} configuration. This configuration defines the number, type and direction of multiple buffers. For BLE products, each buffer is mapped on a characteristic, for wifi product, the buffer ids are sent inside the \ARCode{ARNetworkAL} packets. 4 | 5 | 6 | \subsection{Definition of a Buffer} 7 | 8 | From an external point of view, a buffer is a fifo which will be duplicated on the remote end. Each buffer has 8 parameters. Some of these parameters are for internal use only, while some have an effect on the binary data transmitted on network. The parameters are: 9 | \begin{table}[h] 10 | \centering 11 | \resizebox{\textwidth}{!}{% 12 | \begin{tabular}{|c|c|c|} 13 | \hline 14 | Parameter & Type & Description \\ 15 | \hline 16 | \hline 17 | \ARCode{ID} & \ARCode{int} & The ID of the buffer\\ 18 | & & ([0-255] for wifi, [0-31] for BLE)\\ 19 | \hline 20 | \ARCode{dataType} & \ARCode{eARNETWORKAL_FRAME_TYPE} & The type of the buffer\\ 21 | & & This type will be sent in the \ARCode{ARNetworkAL} frames.\\ 22 | \hline 23 | \ARCode{sendingWaitTimeMs} & \ARCode{int} & Minimum time between two sends\\ 24 | & & (Usually 0, but can be useful to avoid data bursts on network)\\ 25 | \hline 26 | \ARCode{ackTimeoutMs} & \ARCode{int} & Time (in milliseconds) before considering a frame lost\\ 27 | & & (Only used for acknowledged buffers)\\ 28 | \hline 29 | \ARCode{numberOfRetry} & \ARCode{int} & Number of retries before considering a frame lost\\ 30 | & & (Only used for acknowledged buffers)\\ 31 | \hline 32 | \ARCode{numberOfCell} & \ARCode{int32_t} & Size of the internal fifos\\ 33 | \hline 34 | \ARCode{dataCopyMaxSize} & \ARCode{int32_t} & Maximum size of an element in the fifo\\ 35 | \hline 36 | \ARCode{isOverwriting} & \ARCode{int} & Boolean value indicating what to do when\\ 37 | & & data is received while the fifo is full\\ 38 | \hline 39 | \end{tabular} 40 | } 41 | \caption{Parameters for an \ARCode{ARNetwork} buffer} 42 | \end{table} 43 | 44 | 45 | The full configuration parameters for \ARCode{ARNetwork} buffers can be found in\\ 46 | \ARFile{libARNetwork}{Includes/libARNetwork/ARNETWORK_IOBufferParam.h}. 47 | 48 | Each buffer is unidirectional (i.e. can be used to send or receive data, not both), but it is possible to have two buffers (one in each direction) sharing the same ID. Buffers are thus separated in the ``sending'' and ``receiving'' buffers list for each product. 49 | 50 | On these parameters, only \ARCode{ID} and \ARCode{dataType} are actually sent on network. The other ones only dictate the \ARCode{ARNetwork} internal behavior for these buffers. External implementations should follow this behavior too. 51 | 52 | In reception buffers, the \ARCode{dataCopyMaxSize} parameter indicates the maximum size of data (excluding \ARCode{ARNetworkAL} header) that can be read by the library. If a buffer is defined with a \ARCode{dataCopyMaxSize} of 128 in the product, then it will be unable to read a data of 129 or more bytes. 53 | 54 | For emission buffers, the \ARCode{isOverwriting} parameter dictates whether trying to send a data while the sending fifo is full will do a drop of an old data, or a refusal of the new data. For reception buffers, it has almost the same effects, except that refused acknowledged data are NOT acknowledged to the sender (so the sender might retry them later, when the buffer is no longer full). 55 | 56 | For BLE Networks, the \ARCode{ID} is converted to a characteristic number by adding \ARCode{0xf000}. 57 | 58 | 59 | \subsection{Internal buffers} 60 | 61 | 62 | Regardless of the network type, the buffer with ID 0 to 9 are reserved for \ARCode{ARNetwork} internal use. The current implementation uses buffers 0 and 1 to implement a ping with the following protocol: 63 | \begin{itemize} 64 | \item{Send a \ARCode{struct timespec} of the current time to buffer 0} 65 | \item{Wait for reception of the same \ARCode{struct timespec} on buffer 1} 66 | \item{Calculate the difference to estimate the ping} 67 | \end{itemize} 68 | 69 | For this to work, the remote end should immediately send the data on buffer 1 when something is received on buffer 0. If the remote does not implement it, then the estimated latency will always be 1sec, with no further effect on the product. (TL;DR : It is not mandatory for a custom implementation to do this) 70 | 71 | This function is \textbf{disabled} on BLE networks, to avoid sending useless packets. 72 | 73 | Buffers from 2 to 9 are reserved for future use. 74 | 75 | \subsection{Acknowledge buffers} 76 | 77 | Acknowledge buffers are automatically created by \ARCode{ARNetwork} for each buffer (regardless of their type) with the following configuration:\\ 78 | \texttt{\{\\ 79 | .ID = baseId + 128; // (+16 for BLE)\\ 80 | .dataType = ARNETWORKAL\_FRAME\_TYPE\_ACK;\\ 81 | .sendingWaitTimeMs = 0; // Do not wait between data\\ 82 | .ackTimeoutMs = 0; // Unused\\ 83 | .numberOfRetries = 0; // Unused\\ 84 | .numberOfCell = 1; // Never more than one ack at a time\\ 85 | .dataCopyMaxSize = 1; // One byte of data: the sequence number\\ 86 | .isOverwriting = 0; // Useless by design: there is only one ack waiting at a time\\ 87 | \}} 88 | 89 | Acknowledge buffers of sending buffers are added to the receiving buffers list, while acknowledge buffers for receiving buffers are added to the sending buffers list. 90 | 91 | \subsection{Per device buffers} 92 | 93 | \subsubsection{Bebop Drone \& SkyController} 94 | 95 | The Bebop Drone and the SkyController share the same buffer configuration: 96 | 97 | \subsubsection*{Controller to Device buffers} 98 | \begin{itemize} 99 | \item{ 100 | Non ack data (periodic commands for piloting and camera orientation).\\ 101 | This buffers transports \ARCode{ARCommands}.\\ 102 | \texttt{\{}\\ 103 | \texttt{ .ID = 10}\\ 104 | \texttt{ .dataType = ARNETWORKAL\_FRAME\_TYPE\_DATA;}\\ 105 | \texttt{ .sendingWaitTimeMs = 0; // Do not wait between data}\\ 106 | \texttt{ .ackTimeoutMs = 0; // Unused}\\ 107 | \texttt{ .numberOfRetries = 0; // Unused}\\ 108 | \texttt{ .numberOfCell = 2; // PCMD + Camera}\\ 109 | \texttt{ .dataCopyMaxSize = 128;}\\ 110 | \texttt{ .isOverwriting = 1; // Periodic data: most recent is better}\\ 111 | \texttt{\}} 112 | } 113 | \item{ 114 | Ack data (Events, settings ...).\\ 115 | This buffers transports \ARCode{ARCommands}.\\ 116 | \texttt{\{}\\ 117 | \texttt{ .ID = 11}\\ 118 | \texttt{ .dataType = ARNETWORKAL\_FRAME\_TYPE\_DATA\_WITH\_ACK;}\\ 119 | \texttt{ .sendingWaitTimeMs = 0; // Do not wait between data}\\ 120 | \texttt{ .ackTimeoutMs = 150;}\\ 121 | \texttt{ .numberOfRetries = 5;}\\ 122 | \texttt{ .numberOfCell = 20;}\\ 123 | \texttt{ .dataCopyMaxSize = 128;}\\ 124 | \texttt{ .isOverwriting = 0; // Events should not be dropped}\\ 125 | \texttt{\}} 126 | } 127 | \item{ 128 | Emergency data (Emergency command only).\\ 129 | This buffers transports \ARCode{ARCommands}.\\ 130 | \texttt{\{}\\ 131 | \texttt{ .ID = 12}\\ 132 | \texttt{ .dataType = ARNETWORKAL\_FRAME\_TYPE\_DATA\_WITH\_ACK;}\\ 133 | \texttt{ .sendingWaitTimeMs = 0; // Do not wait between data}\\ 134 | \texttt{ .ackTimeoutMs = 150;}\\ 135 | \texttt{ .numberOfRetries = -1; // Infinite}\\ 136 | \texttt{ .numberOfCell = 1;}\\ 137 | \texttt{ .dataCopyMaxSize = 128;}\\ 138 | \texttt{ .isOverwriting = 0; // Events should not be dropped}\\ 139 | \texttt{\}} 140 | } 141 | \item{ 142 | ARStream video acks.\\ 143 | This buffers transports \ARCode{ARStream} data.\\ 144 | \texttt{\{}\\ 145 | \texttt{ .ID = 13}\\ 146 | \texttt{ .dataType = ARNETWORKAL\_FRAME\_TYPE\_DATA\_LOW\_LATENCY;}\\ 147 | \texttt{ .sendingWaitTimeMs = 0; // Do not wait between data}\\ 148 | \texttt{ .ackTimeoutMs = 0; // Unused}\\ 149 | \texttt{ .numberOfRetries = 0; // Unused}\\ 150 | \texttt{ .numberOfCell = 1000; // Enough space ...}\\ 151 | \texttt{ .dataCopyMaxSize = 18; // Size of an ack packet}\\ 152 | \texttt{ .isOverwriting = 1; // New is always better!}\\ 153 | \texttt{\}} 154 | } 155 | \end{itemize} 156 | 157 | 158 | \subsubsection*{Device to Controller buffers} 159 | \begin{itemize} 160 | \item{ 161 | Non ack data (periodic reports from the device).\\ 162 | This buffers transports \ARCode{ARCommands}.\\ 163 | \texttt{\{}\\ 164 | \texttt{ .ID = 127}\\ 165 | \texttt{ .dataType = ARNETWORKAL\_FRAME\_TYPE\_DATA;}\\ 166 | \texttt{ .sendingWaitTimeMs = 20; // Avoid data bursts}\\ 167 | \texttt{ .ackTimeoutMs = 0; // Unused}\\ 168 | \texttt{ .numberOfRetries = 0; // Unused}\\ 169 | \texttt{ .numberOfCell = 20;}\\ 170 | \texttt{ .dataCopyMaxSize = 128;}\\ 171 | \texttt{ .isOverwriting = 1; // Periodic data: most recent is better}\\ 172 | \texttt{\}} 173 | } 174 | \item{ 175 | Ack data (Events, settings ...).\\ 176 | This buffers transports \ARCode{ARCommands}.\\ 177 | \texttt{\{}\\ 178 | \texttt{ .ID = 126}\\ 179 | \texttt{ .dataType = ARNETWORKAL\_FRAME\_TYPE\_DATA\_WITH\_ACK;}\\ 180 | \texttt{ .sendingWaitTimeMs = 0; // Do not wait between data}\\ 181 | \texttt{ .ackTimeoutMs = 150;}\\ 182 | \texttt{ .numberOfRetries = 5;}\\ 183 | \texttt{ .numberOfCell = 256;}\\ 184 | \texttt{ .dataCopyMaxSize = 128;}\\ 185 | \texttt{ .isOverwriting = 0; // Events should not be dropped}\\ 186 | \texttt{\}} 187 | } 188 | \item{ 189 | ARStream video data.\\ 190 | This buffers transports \ARCode{ARStream} data.\\ 191 | \texttt{\{}\\ 192 | \texttt{ .ID = 125}\\ 193 | \texttt{ .dataType = ARNETWORKAL\_FRAME\_TYPE\_DATA\_LOW\_LATENCY;}\\ 194 | \texttt{ .sendingWaitTimeMs = 0; // Do not wait between data}\\ 195 | \texttt{ .ackTimeoutMs = 0; // Unused}\\ 196 | \texttt{ .numberOfRetries = 0; // Unused}\\ 197 | \texttt{ .numberOfCell = *2;}\\ 198 | \texttt{ // Read from ARDiscovery.Discovery part !}\\ 199 | \texttt{ .dataCopyMaxSize = ;}\\ 200 | \texttt{ // Read from ARDiscovery.Discovery part !}\\ 201 | \texttt{ .isOverwriting = 1; // New is always better!}\\ 202 | \texttt{\}} 203 | } 204 | \end{itemize} 205 | 206 | \newpage 207 | 208 | \subsubsection{Jumping Sumo, Jumping Night \& Jumping Race} 209 | 210 | The Jumping Sumo, the Jumping Night and the Jumping Race share the same buffer configuration: 211 | 212 | \subsubsection*{Controller to Device buffers} 213 | \begin{itemize} 214 | \item{ 215 | Non ack data (periodic commands for piloting).\\ 216 | This buffers transports \ARCode{ARCommands}.\\ 217 | \texttt{\{}\\ 218 | \texttt{ .ID = 10}\\ 219 | \texttt{ .dataType = ARNETWORKAL\_FRAME\_TYPE\_DATA;}\\ 220 | \texttt{ .sendingWaitTimeMs = 0; // Do not wait between data}\\ 221 | \texttt{ .ackTimeoutMs = 0; // Unused}\\ 222 | \texttt{ .numberOfRetries = 0; // Unused}\\ 223 | \texttt{ .numberOfCell = 1;}\\ 224 | \texttt{ .dataCopyMaxSize = 128;}\\ 225 | \texttt{ .isOverwriting = 1; // Periodic data: most recent is better}\\ 226 | \texttt{\}} 227 | } 228 | \item{ 229 | Ack data (Events, settings ...).\\ 230 | This buffers transports \ARCode{ARCommands}.\\ 231 | \texttt{\{}\\ 232 | \texttt{ .ID = 11}\\ 233 | \texttt{ .dataType = ARNETWORKAL\_FRAME\_TYPE\_DATA\_WITH\_ACK;}\\ 234 | \texttt{ .sendingWaitTimeMs = 0; // Do not wait between data}\\ 235 | \texttt{ .ackTimeoutMs = 150;}\\ 236 | \texttt{ .numberOfRetries = 5;}\\ 237 | \texttt{ .numberOfCell = 20;}\\ 238 | \texttt{ .dataCopyMaxSize = 128;}\\ 239 | \texttt{ .isOverwriting = 0; // Events should not be dropped}\\ 240 | \texttt{\}} 241 | } 242 | \item{ 243 | ARStream video acks.\\ 244 | This buffers transports \ARCode{ARStream} data.\\ 245 | \texttt{\{}\\ 246 | \texttt{ .ID = 13}\\ 247 | \texttt{ .dataType = ARNETWORKAL\_FRAME\_TYPE\_DATA\_LOW\_LATENCY;}\\ 248 | \texttt{ .sendingWaitTimeMs = 0; // Do not wait between data}\\ 249 | \texttt{ .ackTimeoutMs = 0; // Unused}\\ 250 | \texttt{ .numberOfRetries = 0; // Unused}\\ 251 | \texttt{ .numberOfCell = 1000; // Enough space ...}\\ 252 | \texttt{ .dataCopyMaxSize = 18; // Size of an ack packet}\\ 253 | \texttt{ .isOverwriting = 1; // New is always better!}\\ 254 | \texttt{\}} 255 | } 256 | \item{ 257 | ARStream audio data. (Only for newer models)\\ 258 | This buffers transports \ARCode{ARStream} data.\\ 259 | \texttt{\{}\\ 260 | \texttt{ .ID = 15}\\ 261 | \texttt{ .dataType = ARNETWORKAL\_FRAME\_TYPE\_DATA\_LOW\_LATENCY;}\\ 262 | \texttt{ .sendingWaitTimeMs = 0; // Do not wait between data}\\ 263 | \texttt{ .ackTimeoutMs = 0; // Unused}\\ 264 | \texttt{ .numberOfRetries = 0; // Unused}\\ 265 | \texttt{ .numberOfCell = *2;}\\ 266 | \texttt{ // Read from ARDiscovery.Discovery part !}\\ 267 | \texttt{ .dataCopyMaxSize = ;}\\ 268 | \texttt{ // Read from ARDiscovery.Discovery part !}\\ 269 | \texttt{ .isOverwriting = 1; // New is always better!}\\ 270 | \texttt{\}} 271 | } 272 | \item{ 273 | ARStream audio acks. (Only for newer models)\\ 274 | This buffers transports \ARCode{ARStream} data.\\ 275 | \texttt{\{}\\ 276 | \texttt{ .ID = 14}\\ 277 | \texttt{ .dataType = ARNETWORKAL\_FRAME\_TYPE\_DATA\_LOW\_LATENCY;}\\ 278 | \texttt{ .sendingWaitTimeMs = 0; // Do not wait between data}\\ 279 | \texttt{ .ackTimeoutMs = 0; // Unused}\\ 280 | \texttt{ .numberOfRetries = 0; // Unused}\\ 281 | \texttt{ .numberOfCell = 1000; // Enough space ...}\\ 282 | \texttt{ .dataCopyMaxSize = 18; // Size of an ack packet}\\ 283 | \texttt{ .isOverwriting = 1; // New is always better!}\\ 284 | \texttt{\}} 285 | } 286 | \end{itemize} 287 | 288 | \subsubsection*{Device to Controller buffers} 289 | \begin{itemize} 290 | \item{ 291 | Non ack data (periodic reports from the device).\\ 292 | This buffers transports \ARCode{ARCommands}.\\ 293 | \texttt{\{}\\ 294 | \texttt{ .ID = 127}\\ 295 | \texttt{ .dataType = ARNETWORKAL\_FRAME\_TYPE\_DATA;}\\ 296 | \texttt{ .sendingWaitTimeMs = 20; // Avoid data bursts}\\ 297 | \texttt{ .ackTimeoutMs = 0; // Unused}\\ 298 | \texttt{ .numberOfRetries = 0; // Unused}\\ 299 | \texttt{ .numberOfCell = 20;}\\ 300 | \texttt{ .dataCopyMaxSize = 128;}\\ 301 | \texttt{ .isOverwriting = 1; // Periodic data: most recent is better}\\ 302 | \texttt{\}} 303 | } 304 | \item{ 305 | Ack data (Events, settings ...).\\ 306 | This buffers transports \ARCode{ARCommands}.\\ 307 | \texttt{\{}\\ 308 | \texttt{ .ID = 126}\\ 309 | \texttt{ .dataType = ARNETWORKAL\_FRAME\_TYPE\_DATA\_WITH\_ACK;}\\ 310 | \texttt{ .sendingWaitTimeMs = 0; // Do not wait between data}\\ 311 | \texttt{ .ackTimeoutMs = 150;}\\ 312 | \texttt{ .numberOfRetries = 5;}\\ 313 | \texttt{ .numberOfCell = 256;}\\ 314 | \texttt{ .dataCopyMaxSize = 128;}\\ 315 | \texttt{ .isOverwriting = 0; // Events should not be dropped}\\ 316 | \texttt{\}} 317 | } 318 | \item{ 319 | ARStream video data.\\ 320 | This buffers transports \ARCode{ARStream} data.\\ 321 | \texttt{\{}\\ 322 | \texttt{ .ID = 125}\\ 323 | \texttt{ .dataType = ARNETWORKAL\_FRAME\_TYPE\_DATA\_LOW\_LATENCY;}\\ 324 | \texttt{ .sendingWaitTimeMs = 0; // Do not wait between data}\\ 325 | \texttt{ .ackTimeoutMs = 0; // Unused}\\ 326 | \texttt{ .numberOfRetries = 0; // Unused}\\ 327 | \texttt{ .numberOfCell = *2;}\\ 328 | \texttt{ // Read from ARDiscovery.Discovery part !}\\ 329 | \texttt{ .dataCopyMaxSize = ;}\\ 330 | \texttt{ // Read from ARDiscovery.Discovery part !}\\ 331 | \texttt{ .isOverwriting = 1; // New is always better!}\\ 332 | \texttt{\}} 333 | } 334 | \item{ 335 | ARStream audio acks. (Only for newer models)\\ 336 | This buffers transports \ARCode{ARStream} data.\\ 337 | \texttt{\{}\\ 338 | \texttt{ .ID = 123}\\ 339 | \texttt{ .dataType = ARNETWORKAL\_FRAME\_TYPE\_DATA\_LOW\_LATENCY;}\\ 340 | \texttt{ .sendingWaitTimeMs = 0; // Do not wait between data}\\ 341 | \texttt{ .ackTimeoutMs = 0; // Unused}\\ 342 | \texttt{ .numberOfRetries = 0; // Unused}\\ 343 | \texttt{ .numberOfCell = 1000; // Enough space ...}\\ 344 | \texttt{ .dataCopyMaxSize = 18; // Size of an ack packet}\\ 345 | \texttt{ .isOverwriting = 1; // New is always better!}\\ 346 | \texttt{\}} 347 | } 348 | \item{ 349 | ARStream audio data. (Only for newer models)\\ 350 | This buffers transports \ARCode{ARStream} data.\\ 351 | \texttt{\{}\\ 352 | \texttt{ .ID = 124}\\ 353 | \texttt{ .dataType = ARNETWORKAL\_FRAME\_TYPE\_DATA\_LOW\_LATENCY;}\\ 354 | \texttt{ .sendingWaitTimeMs = 0; // Do not wait between data}\\ 355 | \texttt{ .ackTimeoutMs = 0; // Unused}\\ 356 | \texttt{ .numberOfRetries = 0; // Unused}\\ 357 | \texttt{ .numberOfCell = *2;}\\ 358 | \texttt{ // Read from ARDiscovery.Discovery part !}\\ 359 | \texttt{ .dataCopyMaxSize = ;}\\ 360 | \texttt{ // Read from ARDiscovery.Discovery part !}\\ 361 | \texttt{ .isOverwriting = 1; // New is always better!}\\ 362 | \texttt{\}} 363 | } 364 | \end{itemize} 365 | 366 | \newpage 367 | 368 | \subsubsection{Rolling Spider, Hydrofoil, Airborne Night \& Airborne Cargo} 369 | 370 | The Rolling Spider, the Hydrofoil, the Airborne Night and the Airborne Cargo share the same buffer configuration: 371 | \subsubsection*{Controller to Device buffers} 372 | \begin{itemize} 373 | \item{ 374 | Non ack data (periodic commands for piloting).\\ 375 | This buffers transports \ARCode{ARCommands}.\\ 376 | \texttt{\{}\\ 377 | \texttt{ .ID = 10}\\ 378 | \texttt{ .dataType = ARNETWORKAL\_FRAME\_TYPE\_DATA;}\\ 379 | \texttt{ .sendingWaitTimeMs = 0; // Do not wait between data}\\ 380 | \texttt{ .ackTimeoutMs = 0; // Unused}\\ 381 | \texttt{ .numberOfRetries = 0; // Unused}\\ 382 | \texttt{ .numberOfCell = 1;}\\ 383 | \texttt{ .dataCopyMaxSize = 18; // Maximum size of data on a ble characteristic with a 2 byte header}\\ 384 | \texttt{ .isOverwriting = 1; // Periodic data: most recent is better}\\ 385 | \texttt{\}} 386 | } 387 | \item{ 388 | Ack data (Events, settings ...).\\ 389 | This buffers transports \ARCode{ARCommands}.\\ 390 | \texttt{\{}\\ 391 | \texttt{ .ID = 11}\\ 392 | \texttt{ .dataType = ARNETWORKAL\_FRAME\_TYPE\_DATA\_WITH\_ACK;}\\ 393 | \texttt{ .sendingWaitTimeMs = 0; // Do not wait between data}\\ 394 | \texttt{ .ackTimeoutMs = 150;}\\ 395 | \texttt{ .numberOfRetries = 5;}\\ 396 | \texttt{ .numberOfCell = 20;}\\ 397 | \texttt{ .dataCopyMaxSize = 18;}\\ 398 | \texttt{ .isOverwriting = 0; // Events should not be dropped}\\ 399 | \texttt{\}} 400 | } 401 | \item{ 402 | Emergency data (Emergency command only).\\ 403 | This buffers transports \ARCode{ARCommands}.\\ 404 | \texttt{\{}\\ 405 | \texttt{ .ID = 12}\\ 406 | \texttt{ .dataType = ARNETWORKAL\_FRAME\_TYPE\_DATA\_WITH\_ACK;}\\ 407 | \texttt{ .sendingWaitTimeMs = 0; // Do not wait between data}\\ 408 | \texttt{ .ackTimeoutMs = 150;}\\ 409 | \texttt{ .numberOfRetries = -1; // Infinite}\\ 410 | \texttt{ .numberOfCell = 1;}\\ 411 | \texttt{ .dataCopyMaxSize = 18;}\\ 412 | \texttt{ .isOverwriting = 0; // Events should not be dropped}\\ 413 | \texttt{\}} 414 | } 415 | \end{itemize} 416 | 417 | 418 | \subsubsection*{Device to Controller buffers} 419 | \begin{itemize} 420 | \item{ 421 | Non ack data (periodic reports from the device).\\ 422 | This buffers transports \ARCode{ARCommands}.\\ 423 | \texttt{\{}\\ 424 | \texttt{ .ID = 15}\\ 425 | \texttt{ .dataType = ARNETWORKAL\_FRAME\_TYPE\_DATA;}\\ 426 | \texttt{ .sendingWaitTimeMs = 20; // Avoid data bursts}\\ 427 | \texttt{ .ackTimeoutMs = 0; // Unused}\\ 428 | \texttt{ .numberOfRetries = 0; // Unused}\\ 429 | \texttt{ .numberOfCell = 20;}\\ 430 | \texttt{ .dataCopyMaxSize = 18;}\\ 431 | \texttt{ .isOverwriting = 1; // Periodic data: most recent is better}\\ 432 | \texttt{\}} 433 | } 434 | \item{ 435 | Ack data (Events, settings ...).\\ 436 | This buffers transports \ARCode{ARCommands}.\\ 437 | \texttt{\{}\\ 438 | \texttt{ .ID = 14}\\ 439 | \texttt{ .dataType = ARNETWORKAL\_FRAME\_TYPE\_DATA\_WITH\_ACK;}\\ 440 | \texttt{ .sendingWaitTimeMs = 0; // Do not wait between data}\\ 441 | \texttt{ .ackTimeoutMs = 150;}\\ 442 | \texttt{ .numberOfRetries = 5;}\\ 443 | \texttt{ .numberOfCell = 20;}\\ 444 | \texttt{ .dataCopyMaxSize = 18;}\\ 445 | \texttt{ .isOverwriting = 0; // Events should not be dropped}\\ 446 | \texttt{\}} 447 | } 448 | \end{itemize} 449 | 450 | 451 | %%% Local Variables: 452 | %%% mode: latex 453 | %%% TeX-master: "main" 454 | %%% End: 455 | -------------------------------------------------------------------------------- /Protocol/latex/arnetworkal.tex: -------------------------------------------------------------------------------- 1 | \section{ARNetworkAL protocol} 2 | 3 | The \ARCode{ARNetworkAL} library is responsible for the network abstraction of the \ARCode{ARNetwork} library. Both libraries are really tied together, and the structure of a network packet is composed of header from both, but for the sake of clarity, this section will describe the entire \ARCode{ARNetworkAL+ARNetwork} headers. 4 | 5 | Naming conventions: The full block of data sent by \ARCode{ARNetworkAL} is called a \ARCode{packet}. A \ARCode{packet} is composed of one or more \ARCode{frame}. Each \ARCode{frame} is composed of an \ARCode{header} (Described in this section), and some \ARCode{data} (Described in either \ARCode{ARCommand} or \ARCode{ARStream} section). 6 | 7 | \subsection{Wifi} 8 | 9 | On Wifi network, a \ARCode{packet} is sent on an UDP socket, and corresponds to an UDP packet. The destination ports were negotiated during the \ARCode{ARDiscovery.Connection}, and the sending ports are free. 10 | 11 | 12 | A \ARCode{packet} can contain multiple \ARCode{frames}. \ARCode{frames} are simply added one after another in the UDP packet. 13 | 14 | 15 | A \ARCode{frame} contains the following information: 16 | \begin{itemize} 17 | \item{Data type (1 byte)} 18 | \item{Target buffer ID (1 byte)} 19 | \item{Sequence number (1 byte)} 20 | \item{Total size of the \ARCode{frame} (4 bytes, Little endian)} 21 | \item{Actual data (N bytes)} 22 | \end{itemize} 23 | 24 | \subsubsection{Data types} 25 | 26 | The \ARCode{ARNetworkAL} library supports 4 types of data: 27 | \begin{itemize} 28 | \item{Ack(1): Acknowledgment of previously received data} 29 | \item{Data(2): Normal data (no ack requested)} 30 | \item{Low latency data(3): Treated as normal data on the network, but are given higher priority internally} 31 | \item{Data with ack(4): Data requesting an ack. The receiver must send an ack for this data !} 32 | \end{itemize} 33 | 34 | The full list of data types can be found in the\\ 35 | \ARFile{libARNetworkAL}{Includes/libARNetworkAL/ARNETWORKAL_Frame.h} file. 36 | 37 | 38 | To acknowledge data, simply send back a \ARCode{frame} with the Ack data type, a buffer ID of \ARCode{128+Data_Buffer_ID}, and the data sequence number as the data.\\ 39 | E.g. : To acknowledge the \ARCode{frame} \ARCode{"(hex) 04 0b 42 0b000000 12345678"}, you will need to send a \ARCode{frame} like \ARCode{"(hex) 01 8b 01 08000000 42"} 40 | 41 | \subsubsection{Target Buffer IDs} 42 | 43 | Buffers IDs are separated into three main sections: 44 | \begin{itemize} 45 | \item{[0; 9]: Reserved values for \ARCode{ARNetwork} internal use.} 46 | \item{[10; 127]: Data buffers.} 47 | \item{[128; 255]: Acknowledge buffers.} 48 | \end{itemize} 49 | 50 | By convention, Controller to Product buffers starts at 10 and grow up, while Product to Controller buffers starts at 127 and go down. A buffer number can be used in both direction. 51 | 52 | 53 | A complete description of the buffers will be done in the \ARCode{ARNetwork} section. 54 | 55 | \subsubsection{Sequence number} 56 | 57 | Each buffer has its own independent sequence number, which should be increased on new data send, but not on retries. The \ARCode{ARNetwork} library will ignore out of order and duplicate data, but will still send Acks for them if requested. If the back-gap in sequence number is too high (we use 10 in \ARCode{ARNetwork} library), then the \ARCode{frame} is not considered out of order, and instead is accepted as the new reference sequence number. 58 | 59 | \subsubsection{Multiple \ARCode{frames} in one \ARCode{packet}} 60 | 61 | The \ARCode{packet} \ARCode{"(hex)01ba270800000042020bc30b00000012345678"} can be split in the following way:\ 62 | \begin{itemize} 63 | \item{Read the type of the first \ARCode{frame}: \ARCode(0x01), or Ack} 64 | \item{Read the buffer id of the first \ARCode{frame}: \ARCode(0xba)} 65 | \item{Read the size of the first \ARCode{frame}: \ARCode{0x00000008} (written in human readable endian): 7 bytes of header + 1 byte of data} 66 | \item{Read the data of the first \ARCode{frame}: \ARCode{0x42}} 67 | \item{Since there is remaining data in the buffer, start again the process for a second frame} 68 | \end{itemize} 69 | 70 | For this example, we have an ack for buffer \ARCode{0x0a}, sequence number \ARCode{0x42}, and non acknowledged data for buffer \ARCode{0x0b}, with content \ARCode{0x78563412}. 71 | 72 | 73 | The \ARCode{ARNetworkAL/ARNetwork} libraries should never send ill-formed packets (i.e. every packet you receive consists of [1..N] \ARCode{frames}, without garbage data at the end. These libraries are ill-formed packets resistant: Before reading a \ARCode{frame}, we make sure that there is at least 7 bytes of data remaining in the buffer, before reading data, we make sure that there is at least \ARCode{data_size - 7} bytes of data in the buffer, and so on. 74 | 75 | \subsubsection{Disconnection detection} 76 | 77 | The \ARCode{ARNetworkAL} library will consider the remote to be disconnected if no data was read from the socket for the last 5 seconds. 78 | 79 | \subsection{BLE} 80 | 81 | On BLE networks, a \ARCode{packet} will only encapsulate a single \ARCode{frame}. A \ARCode{frame} is characterized by the BLE characteristic address it belongs to. 82 | 83 | 84 | A \ARCode{frame} contains the following information: 85 | \begin{itemize} 86 | \item{Data type (1 byte)} 87 | \item{Sequence number (1 byte)} 88 | \item{Actual data (up to 18 bytes)} 89 | \end{itemize} 90 | 91 | \subsubsection{Data types} 92 | 93 | The \ARCode{ARNetworkAL} library supports 4 types of data: 94 | \begin{itemize} 95 | \item{Ack(1): Acknowledgment of previously received data} 96 | \item{Data(2): Normal data (no ack requested)} 97 | \item{Low latency data(3): Treated as normal data on the network, but are given higher priority internally} 98 | \item{Data with ack(4): Data requesting an ack. The receiver must send an ack for this data unit!} 99 | \end{itemize} 100 | 101 | The full list of data types can be found in the\\ 102 | \ARFile{libARNetworkAL}{Includes/libARNetworkAL/ARNETWORKAL_Frame.h} file. 103 | 104 | 105 | To acknowledge a data unit, simply send back a \ARCode{frame} with the Ack data type, to the characteristic of id \ARCode{16+characteristic_id}, and the data sequence number as the data.\\ 106 | E.g. : To acknowledge the \ARCode{frame} \ARCode{"(hex) 04 42 12345678"} in characteristic \ARCode{0xf00a}, you will need to send a \ARCode{frame} like \ARCode{"(hex) 01 01 42"} in characteristic \ARCode{0xf01a}. 107 | 108 | \subsubsection{Characteristic IDs} 109 | 110 | 111 | The products should declare 32 characteristics for \ARCode{ARNetwork}, plus 2 for ftp-like purpose (update, media download...). 112 | 113 | 114 | The \ARCode{ARNetwork} characteristics are numbered from \ARCode{0xf000} to \ARCode{0xf01f}. They will be referred as 0 to 31 (just add \ARCode{0xf000} to get the real id). 115 | 116 | 117 | Characteristics are separated into three sections: 118 | \begin{itemize} 119 | \item{[0; 9]: Reserved for \ARCode{ARNetwork} internal use.} 120 | \item{[10; 15]: Data.} 121 | \item{[16; 31]: Acknowledges.} 122 | \end{itemize} 123 | 124 | By convention, the Controller to Product characteristics start a 10 and grow up, while the Product to Controller characteristics start at 15 and go down. A characteristic can be used for two-way communication, but that is not advised (and not used on products). 125 | 126 | 127 | The two characteristics for ftp-like transmission (using \ARCode{ARDataTransfer} library) are \ARCode{0xfd23} and \ARCode{0xfd53}. 128 | 129 | 130 | \subsubsection{Sequence number} 131 | 132 | Each characteristic has its own independent sequence number, which should be increased on new data send, but not on retries. The \ARCode{ARNetwork} library will ignore out of order and duplicate data, but will still send Acks for them if requested. If the back-gap in sequence number is too high (we use 10 in \ARCode{ARNetwork} library), then the \ARCode{frame} is not considered out of order, and instead is accepted as the new reference sequence number. 133 | 134 | %%% Local Variables: 135 | %%% mode: latex 136 | %%% TeX-master: "main" 137 | %%% End: 138 | -------------------------------------------------------------------------------- /Protocol/latex/arstream.tex: -------------------------------------------------------------------------------- 1 | \section{ARStream protocol} 2 | 3 | 4 | The \ARCode{ARStream} library is designed to send and receive arbitraty binary streams using \ARCode{ARNetwork} as its network back-end. It is used to transport live audio and video data between the product and the controller. 5 | 6 | The \ARCode{ARStream} library used an acknowledge system on Bebop Drone firmwares before 2.0.17, while the Jumping Sumo never used them. This feature won't be used on newer firmwares (for all products), so implementing it is optionnal for an \ARCode{ARStream} compatible library. 7 | 8 | 9 | The \ARCode{ARStream} library is not designed to be used on BLE networks. 10 | 11 | \subsection{Terminology} 12 | 13 | \ARCode{ARStream} was designed to transport video data, thus the terms used in this documentation will match some video terms. 14 | 15 | The input of \ARCode{ARStream} is a \ARCode{frame}. A \ARCode{frame} can be a single video frame (for video streams), or multiple audio samples joined togeter (for audio streams). Each frame is also tagged as an \ARCode{FLUSH_FRAME} or not. 16 | 17 | \ARCode{FLUSH_FRAMES} are mapped on I-Frames for \ARCode{h.264} stream (e.g. on Bebop Drone). It is always set for \ARCode{MJPEG} (e.g. Jumping Sumo) and audio streams, as these do not have the I-Frame/P-Frame difference. 18 | 19 | \subsection{Data} 20 | 21 | When sending a \ARCode{frame}, it may be divided in multiple \ARCode{fragments} on the network. The size and the maximum number of fragments are negociated during the ARDiscovery Connection part. 22 | 23 | The data sent to \ARCode{ARNetwork} consists of a packed header followed by the \ARCode{fragment}. 24 | 25 | The header format is: 26 | \begin{itemize} 27 | \item{\ARCode{frameNumber} (2 bytes): Identifier of the frame, if two fragments have the same frame number, they belong to the same frame. This counter loops every $2^{16}$ frames.} 28 | \item{\ARCode{frameFlags} (1 byte): A bitfield indicating flags for the frame. Currenlty only support the \ARCode{FLUSH_FRAME} flag in bit 0.} 29 | \item{\ARCode{fragmentNumber} (1 byte): The index of the current fragment in the frame.} 30 | \item{\ARCode{fragmentsPerFrame} (1 byte): The total number of fragments in the frame.} 31 | \end{itemize} 32 | 33 | The size of the data is not specified, as it can be derived from the size of the \ARCode{ARNetwork} data. The offset is not specified as the library consider that the $N^{th}$ fragment should go at index $arstream\_fragment\_size*N$ (i.e. the library uses only full size fragments, except for the last one which can be shorter). 34 | 35 | Fragments can be received in any order, or even multiple time each. All implementations should accept these cases and keep working. (i.e. do not append data to the output buffer without reading the header!) 36 | 37 | A frame is considered as complete once we receive all of its fragments. If we receive a fragment for frame $N+1$ while the frame $N$ is not complete, then we discard the $N^{th}$ frame and start working on the new one. 38 | 39 | \ARCode{FLUSH_FRAME}s are frames that can be immediately decoded. To reduce latency, \ARCode{FLUSH_FRAME}s should flush any other waiting frame from the pipeline (including any fifo between \ARCode{ARStream} and a video decoder). This behavior is also implemented on the \ARCode{ARStream} sender on the product: if a new \ARCode{FLUSH_FRAME} is available, but some previous frame were not sent, these frames are flushed and the new one is sent instead. 40 | 41 | \subsection{Acknowledges} 42 | 43 | \emph{\ARCode{ARStream} acks are deprecated and are no longer enabled on most products. The description here is only for compatibility with older Bebop Drone firmwares.} 44 | 45 | \ARCode{ARStream} ack policy is controlled by the \ARCode{arstream_max_ack_interval} parameter, negociated during the \ARCode{ARDiscovery} Connection. Most product will send a value of $-1$, which means that no acks are to be sent. 46 | Possible values are: 47 | \begin{itemize} 48 | \item{$-1$ (or other negative value): No ack at all} 49 | \item{$0$: No periodic acks, but send ack when receiving a \ARCode{fragment}} 50 | \item{$>0$: Maximum time (in ms) between two acks. Typically this is done by having a thread sending periodic acks. To keep ack latency as low as possible, keep also sending acks when receiving a \ARCode{fragment}.} 51 | \end{itemize} 52 | 53 | The Acknowledge packet has the following format (packed in memory, so no gap inside the structure): 54 | \begin{itemize} 55 | \item{\ARCode{frameNumber} (2 bytes): Id of the frame (must match the current sending frame).} 56 | \item{\ARCode{highPacketsAck} (8 bytes): Bitfield for the upper 64 fragments of the frame.} 57 | \item{\ARCode{lowPacketsAck} (8 bytes): Bitfield for the lower 64 fragments of the frame.} 58 | \end{itemize} 59 | 60 | To acknowledge a fragment, the corresponding byte in the 128bits bitfield is set, when all fragments bits are set, then the full frame is acknowledged. This structure limits the maximum number of fragments to 128, but the current frimwares only use 4 at most. 61 | 62 | When sending a full ack, it may be useful to set all the bits (even the ones for unused fragment numbers) in the bitfield. This allow the \ARCode{ARStream} late-ack algorithm to work. 63 | 64 | 65 | %%% Local Variables: 66 | %%% mode: latex 67 | %%% TeX-master: "main" 68 | %%% End: 69 | -------------------------------------------------------------------------------- /Protocol/latex/commands.tex: -------------------------------------------------------------------------------- 1 | \newcommand{\ARCode}[1]{\mbox{\texttt{\textbf{\detokenize{#1}}}}} 2 | 3 | \newcommand{\ARFile}[2]{\href{http://github.com/Parrot-Developers/#1/blob/master/#2}{\ARCode{/#1/#2}}} 4 | 5 | %%% Local Variables: 6 | %%% mode: plain-tex 7 | %%% TeX-master: "main" 8 | %%% End: 9 | -------------------------------------------------------------------------------- /Protocol/latex/cover.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Parrot-Developers/Docs/5a59ef23577191e09d35fba41746cee6e39772c1/Protocol/latex/cover.pdf -------------------------------------------------------------------------------- /Protocol/latex/logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Parrot-Developers/Docs/5a59ef23577191e09d35fba41746cee6e39772c1/Protocol/latex/logo.png -------------------------------------------------------------------------------- /Protocol/latex/main.tex: -------------------------------------------------------------------------------- 1 | \documentclass[a4paper,11pt]{article} 2 | 3 | \usepackage[utf8]{inputenc} 4 | \usepackage{hyperref} 5 | \usepackage{graphicx} 6 | \usepackage{pdfpages} 7 | \usepackage{fancyhdr} 8 | 9 | \setcounter{tocdepth}{5} 10 | \setcounter{secnumdepth}{5} 11 | \setlength{\parskip}{1em} 12 | 13 | \input{commands.tex} 14 | 15 | \pagestyle{fancy} 16 | \fancyhf{} 17 | \rhead{ARSDK Protocols} 18 | \lhead{\includegraphics[width=5cm]{logo}} 19 | \cfoot{\thepage} 20 | 21 | \begin{document} 22 | 23 | \includepdf[pages={1}]{cover.pdf} 24 | 25 | \title{ARSDK Protocols} 26 | \author{Parrot SA} 27 | \maketitle 28 | 29 | \newpage 30 | 31 | \tableofcontents 32 | 33 | \newpage 34 | 35 | \input{purpose.tex} 36 | 37 | \newpage 38 | 39 | \input{ardiscovery.tex} 40 | 41 | \newpage 42 | 43 | \input{arnetworkal.tex} 44 | 45 | \newpage 46 | 47 | \input{arnetwork.tex} 48 | 49 | \newpage 50 | 51 | \input{arcommands.tex} 52 | 53 | \newpage 54 | 55 | \input{arstream.tex} 56 | 57 | \end{document} 58 | 59 | %%% Local Variables: 60 | %%% mode: latex 61 | %%% TeX-master: t 62 | %%% End: 63 | -------------------------------------------------------------------------------- /Protocol/latex/purpose.tex: -------------------------------------------------------------------------------- 1 | \addcontentsline{toc}{section}{Purpose of this document} 2 | \section*{Purpose of this document} 3 | 4 | This document describes the binary protocols used by the ARSDK 3, and specifically by the \ARCode{ARNetworkAL}, \ARCode{ARNetwork}, \ARCode{ARDiscovery}, \ARCode{ARStream} and \ARCode{ARCommands} libraries. 5 | 6 | 7 | This document is made for people who want to implement an ARSDK-compatible framework, without reading all the ARSDK source code and trying to figure out ``how it works'' 8 | 9 | \addcontentsline{toc}{section}{Conventions} 10 | \section*{Conventions} 11 | 12 | In this document, products are referred to by their network connection type, rather by their name, so the Bebop Drone and Jumping Sumo (and variants) are ``Wifi products'', while the Rolling Spider (and variants) is a ``BLE product''. If something is specific to a given product, its name will be written directly. 13 | 14 | The connection is done between a controller (the computer, phone, tablet ...) and a device (the Bebop Drone, Rolling Spider ...). In the libraries, some objects are called ``c2d'' or ``d2c'', these notations means ``controller to device'' and ``device to controller'', respectively. 15 | 16 | Inside the ARSDK, the products are sometimes called with other names than the actual product name. Here is a simple list of ARSDK alternative names for real names, which should help when reading the ARSDK source code: 17 | 18 | \begin{table}[h] 19 | \centering 20 | \begin{tabular}{|c|c|} 21 | \hline 22 | Real Name & Alternatives \\ 23 | \hline 24 | \hline 25 | Bebop Drone & ARDrone, ARDrone 3 \\ 26 | \hline 27 | Jumping Sumo & JS \\ 28 | \hline 29 | Rolling Spider & MiniDrone, RS \\ 30 | \hline 31 | SkyController & SC \\ 32 | \hline 33 | Airborne Night & MiniDroneEvoLight \\ 34 | \hline 35 | Airborne Cargo & MiniDroneEvoBrick \\ 36 | \hline 37 | Hydrofoil & MiniDroneEvoHydrofoil \\ 38 | \hline 39 | Jumping Night & JSEvoLight \\ 40 | \hline 41 | Jumping Race & JSEvoRace \\ 42 | \hline 43 | \end{tabular} 44 | \caption{Name correspondence between product names and ARSDK internal names} 45 | \end{table} 46 | 47 | \addcontentsline{toc}{subsection}{Data endianness} 48 | \subsection*{Data endianness} 49 | 50 | For the \ARCode{ARNetwork}, \ARCode{ARNetworkAL}, \ARCode{ARStream} and \ARCode{ARCommands} library, all the data are sent on network in LITTLE\_ENDIAN byte order. This is done because most of the devices actually are in LITTLE\_ENDIAN mode, and thus avoids a lot of byte swapping. 51 | 52 | The \ARCode{ARSAL} library provides conversion macros (similar to the \ARCode{htonl()}-family) in the\\ 53 | \ARFile{libARSAL}{Includes/libARSAL/ARSAL_Endianness.h} file. 54 | 55 | %%% Local Variables: 56 | %%% mode: latex 57 | %%% TeX-master: "main" 58 | %%% End: 59 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | Docs 2 | ==== 3 | 4 | This is the documentation repo. You can here find all the documentation needed to clone and build the ARDroneSDK3. 5 | 6 | Installation 7 | ----------- 8 | All the documentation to install and build the SDK is [here](http://developer.parrot.com/docs/bebop/?objective_c#go-deeper) 9 | 10 | Documentation 11 | ------------- 12 | The SDK documentation is provided [here](http://developer.parrot.com/docs/bebop). It is focused on the Bebop but easily usable for other products. 13 | There is also a [documentation for the SkyController](http://developer.parrot.com/docs/skycontroller/). 14 | If you have any question, feel free to ask them on [our forum](http://forum.developer.parrot.com/). 15 | 16 | Samples 17 | --------- 18 | You can find [samples files](https://github.com/ARDroneSDK3/Samples.git). These samples will help you to build the interface between products and controllers. 19 | Feel free to use and adapt them to your needs. 20 | 21 | License 22 | ------- 23 | Please read the [license file](https://github.com/ARDroneSDK3/Docs/blob/master/LICENSE.md). 24 | -------------------------------------------------------------------------------- /SkyController/.gitignore: -------------------------------------------------------------------------------- 1 | *.toc 2 | latex/main.pdf 3 | *.log 4 | *.out 5 | *.aux 6 | *~ 7 | 8 | _region_.tex 9 | -------------------------------------------------------------------------------- /SkyController/latex/advanced.tex: -------------------------------------------------------------------------------- 1 | \section{Advanced setup} 2 | 3 | \textbf{This section presents some advanced thing you can do with the SkyController system. {\color{red}\emph{These manipulations should only be used if you understand what you're doing, as errors can transform your SkyController into an expensive paperweight!}}} 4 | 5 | \subsection{Root access} 6 | 7 | The SkyController Android version is based on Android 4.2.2. It is a \textit{userdebug} build, meaning that root acces is available. In the same way, it means that the \ARCode{/system} partition can be remounted as read-write. 8 | 9 | \textbf{Warning: abusing root acces can totally brick the device, do not modify any file in /system unless you EXACTLY understand what you're doing!!!} 10 | 11 | \subsection{Uninstalling FreeFlight} 12 | 13 | FreeFlight is installed as a system application, and thus can not be deleted without root access. 14 | 15 | With root access and the \ARCode{/system} partition remonted as read-write, you can close the FreeFlight app, and uninstall it by deleting the \ARCode{/system/app/ARFreeFlight.apk} file. After doing this, you should reboot the SkyController. 16 | 17 | \subsection{Forced update} 18 | 19 | All the \ARCode{/system} partition is rewritten during an update, so updating the SkyController will reinstall FreeFlight if you uninstalled it previously. \emph{Note that the data partition is left untouched during update process, so your app won't be deleted during an update}. 20 | 21 | Should you want to reinstall FreeFlight, you can force the SkyController to update from a USB drive, with the version currently installed (downgrading is not supported and can cause issues during boot !). To do this, connect to your SkyController in a root adb shell, then type the command \ARCode{pinst_trigger}. The following lines should be printed as a response: 22 | 23 | \texttt{shell@android:/ \# pinst\_trigger \\ 24 | sysfs\_read\_int on ubi1:-1 mtd\_num=2 \\ 25 | ubi\_attach on mtd1 : 3 \\ 26 | ubi\_get\_vol\_name on ubi3:1 alt\_boot \\ 27 | ubi\_rename\_boot on ubi3 updater -> 0 \\ 28 | ubi\_detach on ubi3 : 0} 29 | 30 | If any other text is printed, it means that the command did not work (ar you sure you launched it in a root shell ?). 31 | 32 | After running this, reboot the SkyController with a USB drive containing the update file (\ARCode{nap_update.plf}) plugged into the USB port. Note that the SkyController will keep booting in update mode until it successfully find an update file on the USB drive, so it won't be usable between the \ARCode{pinst_trigger} call and the actual update. 33 | 34 | 35 | %%% Local Variables: 36 | %%% mode: latex 37 | %%% TeX-master: "main" 38 | %%% End: -------------------------------------------------------------------------------- /SkyController/latex/changed.tex: -------------------------------------------------------------------------------- 1 | \section{Non-fully integrated features} 2 | 3 | This section presents some of the features that exists on Android phones and on the SkyController, but for which the SkyController API differs from the Android API. 4 | 5 | \subsection{Battery level} 6 | 7 | The battery level is \emph{not} integrated into the Android system, and thus can not be requested through the standard API. It is transmitted to the application as the last axis of the gamepad. 8 | 9 | To convert from the axis value to the battery voltage, you can use the following equation:\\ 10 | \ARCode{float voltage = (float) (((battery + 1) * 1.25) * 1.6) + 9;}\\ 11 | Where \ARCode{battery} is the axis value. To further convert the voltage into a percentage, we use the following equation:\\ 12 | \ARCode{int percent = 100 - (int)(-14.52759414 * Math.pow(voltage, 3)}\\ 13 | \ARCode{ + 543.15310727 * Math.pow(voltage, 2)}\\ 14 | \ARCode{ - 6801.85740495 * voltage}\\ 15 | \ARCode{ + 28532.85560624);} \\ 16 | Which is then saturated between $0$ and $100$. 17 | 18 | %%% Local Variables: 19 | %%% mode: latex 20 | %%% TeX-master: "main" 21 | %%% End: -------------------------------------------------------------------------------- /SkyController/latex/commands.tex: -------------------------------------------------------------------------------- 1 | \newcommand{\ARCode}[1]{\mbox{\texttt{\textbf{\detokenize{#1}}}}} 2 | 3 | \newcommand{\ARConfig}[1]{\paragraph{\ARCode{#1}}} 4 | 5 | \newcommand{\ARFile}[2]{\href{http://github.com/Parrot-Developers/#1/blob/master/#2}{\ARCode{/packages/#1/#2}}} 6 | 7 | %%% Local Variables: 8 | %%% mode: plain-tex 9 | %%% TeX-master: "main" 10 | %%% End: 11 | -------------------------------------------------------------------------------- /SkyController/latex/connection.tex: -------------------------------------------------------------------------------- 1 | \section{Handling ARSDK connections} 2 | 3 | \subsection{Connecting to a drone} 4 | 5 | Connection to a drone is done in the same was as on any other Android device. Any app working on phones/tablet should work on the SkyController, as long as the UI is adapted to the DPAD navigation and the screen size. 6 | 7 | \subsection{Connecting to a tablet/smartphone} 8 | 9 | The actual code to handle incoming connections is part of the FreeFlight application embedded on SkyControllers. The code is not open-sourced, but it is implemented using components avaible in the ARSDK. 10 | 11 | \subsubsection{Publishing a mDNS service} 12 | 13 | To be discoverable on the network, the application should publish a mDNS service with the proper type (\ARCode{_arsdk-0903._udp.local}). 14 | 15 | \subsubsection{Accepting incoming ARSDK connections} 16 | 17 | To accept a connection, the application should have an instance of an \ARCode{ARDISCOVERY_Connection} object, running the \ARCode{ARDISCOVERY_Connection_DeviceListeningLoop()} method. This discover server will then negociate connection as would a drone do. A complete rundown of the \ARCode{ARDiscovery} protocol is available in the \href{http://developer.parrot.com//docs/bebop/ARSDK_Protocols.pdf}{ARSDK protocols documentation}. 18 | 19 | \subsubsection{Creating the ARNetwork instances} 20 | 21 | The ARNetwork instance can be created with the parameters from the Discovery phase. The instance is then used in the same way as a client instance (the ARNetwork protocol is peer to peer). 22 | 23 | \subsubsection{Routing commands} 24 | 25 | The minimum routing rules for the commands are the following: 26 | 27 | \begin{itemize} 28 | \item All \ARCode{ARCommands} received from the drone must be sent to the tablet (if present) 29 | \item All \ARCode{ARCommands} received from the tablet must be sent to the drone (if present), except for the SkyController.X.Y commands (see \ARCode{ARCOMMANDS_Filter}) 30 | \end{itemize} 31 | 32 | \emph{Note: In order to grab the \ARCode{ARCommands}, you can't use the \ARCode{ARController} API, as it hides this part of the protocol.} 33 | 34 | \subsubsection{Routing video} 35 | 36 | Routing an \ARCode{ARStream1} stream is done in the same way as routing the commands: All stream packets received from the drone are sent to the tablet (at the \ARCode{ARNetwork} level). 37 | 38 | Routing an \ARCode{ARStream2} stream is done by using the \ARCode{libARStream2} library, and specifically the \ARCode{resender}-related functions. You can find informations about this API in the following file:\\ 39 | \ARFile{libARStream2}{Includes/libARStream2/arstream2_stream_receiver.h} 40 | 41 | 42 | %%% Local Variables: 43 | %%% mode: latex 44 | %%% TeX-master: "main" 45 | %%% End: -------------------------------------------------------------------------------- /SkyController/latex/cover.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Parrot-Developers/Docs/5a59ef23577191e09d35fba41746cee6e39772c1/SkyController/latex/cover.pdf -------------------------------------------------------------------------------- /SkyController/latex/generic.tex: -------------------------------------------------------------------------------- 1 | \section{Advanced setup} 2 | 3 | \textit{This section presents some advanced thing you can do with the SkyController system. These manipulations should only be used if you understand what you're doing, as errors can transform your SkyController into an expensive paperweight!} 4 | 5 | \subsection{Root access} 6 | 7 | The SkyController Android version is based on Android 4.2.2. It is a \textit{userdebug} build, meaning that root acces is available. In the same way, it means that the \ARCode{/system} partition can be remounted as read-write. 8 | 9 | \textbf{Warning: abusing root acces can totally brick the device, do not modify any file in /system unless you EXACTLY understand what you're doing!!!} 10 | 11 | \subsection{Uninstalling FreeFlight} 12 | 13 | FreeFlight is installed as a system application, and thus can not be deleted without root access. 14 | 15 | With root access and the \ARCode{/system} partition remonted as read-write, you can close the FreeFlight app, and uninstall it by deleting the \ARCode{/system/app/ARFreeFlight.apk} file. After doing this, you should reboot the SkyController. 16 | 17 | \subsection{Forced update} 18 | 19 | All the \ARCode{/system} partition is rewritten during an update, so updating the SkyController will reinstall FreeFlight if you uninstalled it previously. \emph{Note that the data partition is left untouched during update process, so your app won't be deleted during an update}. 20 | 21 | Should you want to reinstall FreeFlight, you can force the SkyController to update from a USB drive, with the version currently installed (downgrading is not supported and can cause issues during boot !). To do this, connect to your SkyController in a root adb shell, then type the command \ARCode{pinst_trigger}. The following lines should be printed as a response: 22 | 23 | \texttt{shell@android:/ \# pinst\_trigger \\ 24 | sysfs\_read\_int on ubi1:-1 mtd\_num=2 \\ 25 | ubi\_attach on mtd1 : 3 \\ 26 | ubi\_get\_vol\_name on ubi3:1 alt\_boot \\ 27 | ubi\_rename\_boot on ubi3 updater -> 0 \\ 28 | ubi\_detach on ubi3 : 0} 29 | 30 | If any other text is printed, it means that the command did not work (ar you sure you launched it in a root shell ?). 31 | 32 | After running this, reboot the SkyController with a USB drive containing the update file (\ARCode{nap_update.plf}) plugged into the USB port. Note that the SkyController will keep booting in update mode until it successfully find an update file on the USB drive, so ti won't be usable between the \ARCode{pinst_trigger} call and the actual update. 33 | 34 | 35 | %%% Local Variables: 36 | %%% mode: latex 37 | %%% TeX-master: "main" 38 | %%% End: -------------------------------------------------------------------------------- /SkyController/latex/logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Parrot-Developers/Docs/5a59ef23577191e09d35fba41746cee6e39772c1/SkyController/latex/logo.png -------------------------------------------------------------------------------- /SkyController/latex/main.tex: -------------------------------------------------------------------------------- 1 | \documentclass[a4paper,11pt]{article} 2 | 3 | \usepackage[utf8]{inputenc} 4 | \usepackage{hyperref} 5 | \usepackage{graphicx} 6 | \usepackage{pdfpages} 7 | \usepackage{fancyhdr} 8 | \usepackage{titlesec} 9 | \usepackage{listings} 10 | 11 | \titleformat{\paragraph} 12 | {\normalfont\normalsize\bfseries}{\theparagraph}{1em}{} 13 | \titlespacing*{\paragraph} 14 | {0pt}{3.25ex plus 1ex minus .2ex}{1.5ex plus .2ex} 15 | 16 | \setcounter{tocdepth}{3} 17 | \setcounter{secnumdepth}{3} 18 | \setlength{\parskip}{1em} 19 | 20 | \input{commands.tex} 21 | 22 | \pagestyle{fancy} 23 | \fancyhf{} 24 | \rhead{Developing on the SkyController} 25 | \lhead{\includegraphics[width=5cm]{logo}} 26 | \cfoot{\thepage} 27 | 28 | \begin{document} 29 | 30 | \includepdf[pages={1}]{cover.pdf} 31 | 32 | \title{Developing applications for the SkyController} 33 | \author{Parrot SA} 34 | \maketitle 35 | 36 | \newpage 37 | 38 | \tableofcontents 39 | 40 | \newpage 41 | 42 | \input{purpose.tex} 43 | 44 | \newpage 45 | 46 | \input{setup.tex} 47 | 48 | \newpage 49 | 50 | \input{advanced.tex} 51 | 52 | \newpage 53 | 54 | \input{same.tex} 55 | 56 | \newpage 57 | 58 | \input{changed.tex} 59 | 60 | \newpage 61 | 62 | \input{new.tex} 63 | 64 | \newpage 65 | 66 | \input{connection.tex} 67 | 68 | \end{document} 69 | 70 | %%% Local Variables: 71 | %%% mode: latex 72 | %%% TeX-master: t 73 | %%% End: 74 | -------------------------------------------------------------------------------- /SkyController/latex/new.tex: -------------------------------------------------------------------------------- 1 | \section{SkyController specific features} 2 | 3 | This section describes some features specific to the SkyController, and completely inexistant in other Android devices. Almost all of these features are using binaries and scripts to work, and are not wrapped into Java APIs. 4 | 5 | \subsection{LEDs control} 6 | 7 | The SkyController has 16 leds, divided into 4 visual banks: 8 | \begin{itemize} 9 | \item 1 red led for the record indicator. Id: 0 10 | \item 1 red and 4 while leds for the wifi indicator. The red led shares the leftmost position with a white led. Ids: 1 (red), 2,3,4,5 (white) 11 | \item 1 red and 4 while leds for the local battery indicator. The red led shares the leftmost position with a white led. Ids: 6 (red), 7,8,9,10 (white) 12 | \item 1 red and 4 while leds for the drone battery indicator. The red led shares the leftmost position with a white led. Ids: 11 (red), 12,13,14,15 (white) 13 | \end{itemize} 14 | 15 | A command to the LED driver will update the 16 leds at once, and it is not possible to read the current LED state from the driver, so your application will have to save the requested state in order to allow toggles of individual leds. If blinking is required, it should be implemented in your application (i.e. toggle a led every N sec). 16 | 17 | The system does not drive any led, all indicators should be updated from within your application (as FreeFlight does). 18 | 19 | \newpage 20 | \subsubsection{LED protocol} 21 | 22 | The LED driver is connected through an SPI interface, driven by GPIOs. The \ARCode{/sys/class/gpio/gpio/value} files are writeable by everyone, so you don't need root access to use the leds. 23 | 24 | Here is a table of the 4 GPIOs numbers and names: 25 | \begin{table}[h] 26 | \centering 27 | \begin{tabular}{|c|c|} 28 | \hline 29 | GPIO Nr & Usage \\ 30 | \hline 31 | \hline 32 | 55 & SPI Clock \\ 33 | \hline 34 | 56 & Latch signal \\ 35 | \hline 36 | 57 & Blank signal \\ 37 | \hline 38 | 58 & SPI MOSI \\ 39 | \hline 40 | \end{tabular} 41 | \end{table} 42 | 43 | Here is a pseudocode representing a send to the driver:\\ 44 | \begin{lstlisting}[frame=single] 45 | set_leds (boolean leds[16]) { 46 | for (i=0; i<16; i++) { 47 | SPI_MOSI = leds[i]; 48 | SPI_CLOCK = 1; 49 | SPI_CLOCK = 0; 50 | } 51 | BLANK = 1; 52 | LATCH = 1; 53 | LATCH = 0; 54 | BLANK = 0; 55 | } 56 | \end{lstlisting} 57 | 58 | The \ARCode{/system/xbin/setleds} script gives an example of how to use the driver. This script will light the leds whose IDs are given as command line arguments. 59 | 60 | 61 | \subsection{Gamepad modes} 62 | 63 | The SkyController gamepad can be configured into two modes: a compatibility mode, which use the top-left joystick as a mouse, and a full-gamepad mode which uses the top-left joystick as the DPAD controls. 64 | 65 | \subsubsection{Compatibility mode} 66 | 67 | This is the default mode when booting, or after exiting FreeFlight. In this mode, the top-left joystick is used a a mouse, for compatibility with apps not designed for DPAD navigation. 68 | 69 | This mode uses the left joystick as the DPAD, with the TakeOff button having the DPAD\_CENTER fallback function. The back and home (settings, on black SkyControllers) are mapped to either L2/R2 (with Back/Home as fallbacks) when an HDMI screen is plugged, or L1/R1 (without fallbacks) when no HDMI screen is plugged. This is a protection to avoid exiting an application without a screen. The return-to-home button has a fallback to the APP\_SWITCH feature. 70 | 71 | Fallback functions are triggered only if the running application did not handle (i.e. return \ARCode{true} in the \ARCode{dispatchKeyEvent()} function) the primary event, so by handling all primary event, you can prevent fallbacks features to be triggered. 72 | 73 | \subsubsection{Full gamepad mode} 74 | 75 | This mode is used by the FreeFlight app, and can be used by any application which supports a full DPAD navigation. In this mode, the top-left joystick is used as a DPAD, and the joystick click has the DPAD\_CENTER fallback function. 76 | 77 | Contrary to the compatibility mode, this mode home (settings, on black SkyControllers) and back buttons behavior does not change when a screen is plugged or not : the back button is always mapped to L2 (with BACK fallback), and the home/settings is mapped to R1 (without fallback). Other mappings (and axis numbering) will differ between the two modes. 78 | 79 | \subsubsection{Changing the mode} 80 | 81 | Changing the mode is done through the \ARCode{atmegCheckUpdate} script, which is in the SkyController PATH. This script has many uses which are not covered by this document, but the mode switch command works in the following way: 82 | 83 | \begin{itemize} 84 | \item \ARCode{atmegCheckUpdate mode FREEFLIGHT} : put the gamepad in full gamepad mode (the mode used by FreeFlight) 85 | \item \ARCode{atmegCheckUpdate mode HOME_SCREEN} : put the gamepad in compatibility mode, as if a screen is currently plugged 86 | \item \ARCode{atmegCheckUpdate mode HOME_NOSCREEN} : put the gamepad in compatibility mode, as if a no screen is present 87 | \end{itemize} 88 | 89 | \emph{Note: When in \ARCode{HOME_XXX} mode, the mode will automatically whange its screen settings on HDMI hotplug/unplug events} 90 | 91 | \subsection{Screen detection} 92 | 93 | The presence of an HDMI screen is indicated by the \ARCode{hw.external_screen} system property. A value of $"1"$ means that an external screen is plugged, any other value means that no screen is plugged. 94 | 95 | \newpage 96 | \subsection{SkyController configuration} 97 | 98 | The SkyController system configuration is done through a system similar to the Android property system. Accessing this configuration is done through the \ARCode{SCConfig} binary. Main commands are: 99 | 100 | \begin{itemize} 101 | \item \ARCode{SCConfig dump} : Dumps the current config in stdout. 102 | \item \ARCode{SCConfig set KEY VALUE} : Sets the config KEY to the value VALUE 103 | \item \ARCode{SCConfig remove KEY} : Remove the config KEY, if present 104 | \item \ARCode{SCConfig get KEY [DEFAULT]} : Get the value associated with KEY. \\ 105 | If KEY is not present, then DEFAULT will be returned (or an empty string if DEFAULT is not provided) 106 | \end{itemize} 107 | 108 | \emph{Note: Using a bad configuration might disable the wifi on the SkyController. Before changing the configuration, you should make a copy of the previous configuration, and switch back to this copy if anything fails} 109 | 110 | \emph{Note: The configuration is stored in the \ARCode{/data/skycontroller/config} file. You should NOT modify this file directly. The \ARCode{SCConfig} tool handles concurrent access and file locking.} 111 | 112 | \subsubsection{Common configuration keys} 113 | 114 | Here is a list of the common configuration keys: 115 | 116 | \ARConfig{KEEP_FF_RUNNING} 117 | 118 | This config key should always be $"0"$. A different value means that a system daemon will try to restart FreeFlight when it's not running. FreeFlight sets this value to $"1"$ when starting, and resets it to $"0"$ when exiting properly. 119 | 120 | \ARConfig{WIFI_BAND} 121 | 122 | The requested band of the access point. $"0"$ means 2.4GHz, $"1"$ means 5GHz, other values have undefined behavior. 123 | 124 | \emph{Note: This key is only applied when the \ARCode{WIFI_REQUEST_APPLY_SETTINGS} is set to $"1"$} 125 | 126 | \ARConfig{WIFI_CHANNEL} 127 | 128 | The requested channel of the access point, within the selected band. If an invalid band/channel combination is given, the system will select a default one. 129 | 130 | \emph{Note: This key is only applied when the \ARCode{WIFI_REQUEST_APPLY_SETTINGS} is set to $"1"$} 131 | 132 | \ARConfig{WIFI_COUNTRY} 133 | 134 | The requested country for all wifi (both access point and long range). This setting changes both the Tx powers and the valid channels/bands. Value is a 2 character country code (e.g. $"US"$, $"FR"$, ...). Putting an unknown country code will set the SkyController wifi to an universal mode (low power, few channels available). 135 | 136 | \emph{Note: This key is only applied when the \ARCode{WIFI_REQUEST_APPLY_SETTINGS} is set to $"1"$} 137 | 138 | \emph{Note: Changing the country will lead to a long range wifi disconnection as the wireless driver needs to be reloaded in order to change the regulatory domain.} 139 | 140 | \emph{Note: Some SkyController are locked to a specific country, and chaning this key won't have any effect on these devices. The \ARCode{WIFI_COUNTRY_APPLIED} will always reflect the actual applied country.} 141 | 142 | \ARConfig{WIFI_SSID} 143 | 144 | The SSID of the SkyController's AP. The value will be filtered (stripping invalid characters, shortening if necessary) by the system before being applied, but values should be strings of less than 32 charactes. It should be matched by the following regexp: \ARCode{"^[-_a-zA-Z0-9]{1,32}\$"}. 145 | 146 | \emph{Note: This key is only applied when the \ARCode{WIFI_REQUEST_APPLY_SETTINGS} is set to $"1"$} 147 | 148 | \ARConfig{WIFI_REQUEST_UPDATE_SETTINGS} 149 | 150 | Set this key to $"1"$ to apply all pending \ARCode{WIFI_XXX} configuration. Almost all configuration changes will triger an access point stop/start, thus disconnecting any connected device. 151 | 152 | This key will be set back to $"0"$ by the system after application. 153 | 154 | \ARConfig{WIFI_XXX_APPLIED} 155 | 156 | These keys shows the applied wifi settings. 157 | \begin{itemize} 158 | \item \ARCode{WIFI_APPLIED_CTL} : The power domain applied for the current wifi country. 159 | \item \ARCode{WIFI_APPLIED_REG_DOMAIN} : The regulatory domain applied for the current wifi country. 160 | \item \ARCode{WIFI_COUNTRY_APPLIED} : The actual wifi country. 161 | \item \ARCode{WIFI_SSID_APPLIED} : The actual access point SSID. 162 | \item \ARCode{WIFI_BAND_APPLIED} : The actual access point band. 163 | \item \ARCode{WIFI_CHANNEL_APPLIED} : The actual access point channel. 164 | \end{itemize} 165 | 166 | %%% Local Variables: 167 | %%% mode: latex 168 | %%% TeX-master: "main" 169 | %%% End: -------------------------------------------------------------------------------- /SkyController/latex/purpose.tex: -------------------------------------------------------------------------------- 1 | \addcontentsline{toc}{section}{Purpose of this document} 2 | \section*{Purpose of this document} 3 | 4 | This document describes the differences between the Parrot SkyController and other Android devices. 5 | 6 | It is designed for Android developers which want to make apps that run directly on the Parrot SkyController, it does not cover the topic of using the ARSDK (see the Android samples for this). 7 | 8 | 9 | %%% Local Variables: 10 | %%% mode: latex 11 | %%% TeX-master: "main" 12 | %%% End: 13 | -------------------------------------------------------------------------------- /SkyController/latex/same.tex: -------------------------------------------------------------------------------- 1 | \section{Fully integrated features} 2 | 3 | Some of the SkyController features are fully integrated into the Android API. Here is a list of such features. 4 | 5 | \subsection{Wifi} 6 | 7 | The \emph{long range} wifi (\ARCode{wlan0}) is managed through the Android WifiManager interface (as you would manage the WiFi on a phone or tablet), except for the country selection. 8 | 9 | Country is persistent across reboots and updates, so you should almost never have to change it. \emph{Note that some SkyController are locked to a given country due to regulations.} 10 | 11 | \subsection{Sensors} 12 | 13 | The SkyController GPS sensor is fully integrated into the Android APIs. The same goes for the Accelerometer, Gyroscope and Magnetometer sensors. The Orientation sensor is used as the sensor fusion result and should be used if your app requires the attitude or the heading of the SkyController. 14 | 15 | \emph{Note : The SkyController magnetometer calibration status is avaible through the \ARCode{accuracy} field of the Magnetometer and Orientation SensorEvents. The precise measurement of the calibration use a custom protocol that is likely to change between versions and is not discussed here.} 16 | 17 | \subsection{Gamepad} 18 | 19 | The SkyController joysticks and buttons are seen as a USB gamepad, sending MotionEvents and KeyEvents to the applications. You can use it as any other USB gamepad on Android. 20 | 21 | One of the gamepad axis will actually be an image of the battery voltage, and is detailed in the next section. 22 | 23 | %%% Local Variables: 24 | %%% mode: latex 25 | %%% TeX-master: "main" 26 | %%% End: -------------------------------------------------------------------------------- /SkyController/latex/setup.tex: -------------------------------------------------------------------------------- 1 | \section{Environment setup} 2 | 3 | \subsection{Requirements} 4 | 5 | In order to develop for the Parrot SkyController, you need a working Android development environment, able to deploy application on Android 4.2.2 targets. 6 | 7 | A good understanding of adb shell commands can also be useful, as a lot of the SkyController configuration is done by stand-alone programs and shell scripts, and not by a Java API. 8 | 9 | \subsection{Configuring ADB} 10 | 11 | The SkyController has a micro-usb port, which is used both for device flashing (\textit{not covered in this document}) and for adb access. When starting the SkyController, you \textbf{must} unplug the micro-usb cable, else it will start in flashing mode and won't be usable for development. 12 | 13 | The SkyController USB vendor ID is \ARCode{0x0525}, and must be added to your \ARCode{adb_usb.ini} file. On Linux (and other Unix-likes, like Mac OSx), this file is located in the \ARCode{~/.android/} directory. 14 | 15 | After adding the USB vendor ID to the \ARCode{adb_usb.ini} file, you should restart your adb server (\ARCode{adb kill-server; adb start-server}). At this point, you should be able to see the SkyController in the list of adb devices. 16 | 17 | \subsection{Adding peripherals} 18 | 19 | By default, the SkyController supports a wide range of HDMI screens and USB peripherals. For ease of development, using an HDMI screen and a USB mouse is advised. Some touch screens with USB interface might also work. 20 | 21 | Of course you can also work with the built-in controls and no display, but it might be more difficult for you to start developing in this setup. 22 | 23 | \subsection{Stopping FreeFlight on the SkyController} 24 | 25 | By default, the SkyController launches FreeFlight at start-up. 26 | 27 | In order to stop FreeFlight, the easiest solution is to use an HDMI screen, and to leave the FreeFlight app by using the Back button and clicking OK on the confirmation dialog. By doing this, FreeFlight will a) reset the gamepad mode to the default one (more on that later) and b) stop the system daemon from restarting it. If FreeFlight is force-killed (or crashes), a system daemon will restart it automatically. 28 | 29 | You can also completely uninstall FreeFlight from the SkyController, but you will need to force-update the SkyController to reinstall the app (\emph{i.e. you can't install an APK from the Play Store, they're not exactly the same application !}) 30 | 31 | \subsection{Ready to develop} 32 | 33 | If you can see your SkyController on adb, and you have properly closed FreeFlight, you're ready to start! 34 | 35 | 36 | %%% Local Variables: 37 | %%% mode: latex 38 | %%% TeX-master: "main" 39 | %%% End: 40 | --------------------------------------------------------------------------------