Skip to content

Commit

Permalink
[export] export PPRZ datalink macros
Browse files Browse the repository at this point in the history
useful when working with external project who wants to avoid coding
the datalink parser and message protocol
  • Loading branch information
gautierhattenberger committed Feb 7, 2014
1 parent 8af1bda commit 0a13cfe
Show file tree
Hide file tree
Showing 7 changed files with 308 additions and 2 deletions.
72 changes: 72 additions & 0 deletions sw/airborne/subsystems/datalink/Makefile
@@ -0,0 +1,72 @@
#
# Copyright (C) 2013 Gautier Hattenberger
#
# This file is part of paparazzi.
#
# paparazzi is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 2, or (at your option)
# any later version.
#
# paparazzi is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with paparazzi; see the file COPYING. If not, write to
# the Free Software Foundation, 59 Temple Place - Suite 330,
# Boston, MA 02111-1307, USA.
#

#
# Export downlink library source code using PPRZ transport protocol
#
# The library as to be compiled by the target application
# after implementing the dl_parse function (for parsing incoming messages)
#

# Quiet compilation
Q=@

TAR= tar
INCLUDES= -I$(PAPARAZZI_SRC)/sw/include -I$(PAPARAZZI_SRC)/sw/airborne

ifeq ($(PAPARAZZI_HOME),)
PAPARAZZI_HOME=$(PAPARAZZI_SRC)
endif

# export in $(PAPARAZZI_HOME)/var/export/datalink
EXPORT_ROOT ?= $(PAPARAZZI_HOME)/var/export
EXPORT_DIR = $(EXPORT_ROOT)/datalink

EXPORT_FILES = \
downlink.h \
downlink.c \
pprz_transport.h \
pprz_transport.c \
transport.h \
datalink.h \
$(PAPARAZZI_SRC)/sw/include/std.h \
$(PAPARAZZI_HOME)/var/include/messages.h \
$(PAPARAZZI_HOME)/var/include/dl_protocol.h

MAKEFILE_EXPORT = pprz_datalink.mk
TAR_EXPORT = pprz_datalink.tar

all:
@cat README

export_lib:
@echo Exporting datalink lib to $(EXPORT_DIR)
$(Q)test -d $(EXPORT_DIR) || mkdir -p $(EXPORT_DIR)
$(Q)cp $(EXPORT_FILES) $(EXPORT_DIR)
$(Q)cp $(MAKEFILE_EXPORT) $(EXPORT_DIR)
$(Q)cp README.md $(EXPORT_DIR)
$(Q)cd $(EXPORT_ROOT); $(TAR) -cf $(TAR_EXPORT) datalink/*

clean:
$(Q)rm -rf $(EXPORT_DIR)

.PHONY: all clean export_lib

179 changes: 179 additions & 0 deletions sw/airborne/subsystems/datalink/README.md
@@ -0,0 +1,179 @@
Datalink (uplink and downlink) lib using PPRZ protocol
======================================================

HOWTO export
------------

- Export library: in this folder, type
```
make export_lib
```
be sure that you have correctly build the paparazzi project (`make` in the main directory)

- The default export directory is `${PAPARAZZI_HOME}/var/export`, to change it:
```
EXPORT_ROOT=<your_export_root_dir> make export_lib
```

- `make clean` will only remove the export directory

HOWTO use the datalink library
------------------------------

1. Copy the folder `datalink` in the export directory to your project directory (or untar the file `pprz_datalink.tar`)

2. In your project makefile:
* define the variable `PPRZ_DATALINK_PORT` to your device (ex: `PPRZ_DATALINK_PORT=XXX`)
* define the variable `PPRZ_DATALINK_DIR` to your extract folder
* include the library makefile `include ${PPRZ_DATALINK_DIR}/datalink/pprz_datalink.mk`
* add `PPRZ_DATALINK_CFLAGS` to your cflags
* add `PPRZ_DATALINK_SRCS` to your sources (if your project requires a list of object files, you can use `PPRZ_DATALINK_OBJS` instead)

3. Device interface
You need to provide an interface to send the data. If your device is named `XXX`, you need to provide the following functions or macros
* `XXXCheckFreeSpace(len)` that return true if your device has enough space for `len` bytes
* `XXXTransmit(c)` that send a single byte `c` using the device `XXX` (or store them in a buffer)
* `XXXSendMessage()` that flushs the bytes to send (if needed)
* `XXXChAvailable()` that returns true new characters are available for reading
* `XXXGetch()` taht returns the next character to parse

Usually, an UART interface is used for datalink.

4. Message parsing and includes:
in a C file of you project (for example a file named `datalink.c`), add the following lines:
```
#define DATALINK_C 1 // this should be placed before the includes
#inlcude "uart.h" // or change this include to the header of your actual device interface
#include "downlink.h"
void dl_parse_msg(void) {
<add your code to parse messages here>
}
```
You also need to poll for new characters, which means that you have to call the `DatalinkEvent()` function in your main loop.
This function is non-blocking and calls the decoder on each received byte. Finally the `dl_parse_msg` function is called when a complete message is received (checksum is valid).

Example project for Mbeb dev board
==================================

Test file `test_dl.cpp` (assuming you already have the Mbed library)
```
#include "mbed.h"
Ticker daq;
Serial uart1(p9, p10);
DigitalOut led1(LED1);
DigitalOut led2(LED2);
/**** PPRZ interface ****/
#define DATALINK_C 1
#define UartCheckFreeSpace(_len) uart1.writeable()
#define UartTransmit(_c) uart1.putc(_c)
#define UartSendMessage() {}
#define UartChAvailable() uart1.readable()
#define UartGetch() uart1.getc()
#include "downlink.h"
void dl_parse_msg(void) {
int msg_id = dl_buffer[1];
switch (msg_id) {
case DL_PONG:
led2 =! led2; // toggle led on new PONG message
break;
default:
break;
}
}
/************************/
void cb()
{
// Toggle led 1 when sending PING
led1 =! led1;
// Send PPRZ message
DOWNLINK_SEND_PING(DefaultChannel, DefaultDevice);
}
int main()
{
uart1.baud(57600); // set serial baud rate for PPRZ
led1 = led2 = 0; // turn off all LEDs
daq.attach(&cb, 1); // callback
while(1) {
// Your (non-blocking) code
// Poll new bytes on uart
DatalinkEvent();
} // ~while
} // ~main
```

With the makefile:
```
# This file was automagically generated by mbed.org with PPRZ datalink library addition
GCC_BIN = /usr/bin/
PROJECT = Test_PPRZ_Datalink
OBJECTS = ./test_dl.o
SYS_OBJECTS = ./mbed/LPC1768/GCC_CS/sys.o ./mbed/LPC1768/GCC_CS/cmsis_nvic.o ./mbed/LPC1768/GCC_CS/system_LPC17xx.o ./mbed/LPC1768/GCC_CS/core_cm3.o ./mbed/LPC1768/GCC_CS/startup_LPC17xx.o
INCLUDE_PATHS = -I. -I./mbed -I./mbed/LPC1768 -I./mbed/LPC1768/GCC_CS
LIBRARY_PATHS = -L./mbed/LPC1768/GCC_CS
LIBRARIES = -lmbed -lcapi
LINKER_SCRIPT = ./mbed/LPC1768/GCC_CS/LPC1768.ld
CC = $(GCC_BIN)arm-none-eabi-gcc
CPP = $(GCC_BIN)arm-none-eabi-g++
CC_FLAGS = -c -Os -fno-common -fmessage-length=0 -Wall -fno-exceptions -mcpu=cortex-m3 -mthumb -ffunction-sections -fdata-sections
ONLY_C_FLAGS = -std=gnu99
ONLY_CPP_FLAGS = -std=gnu++98
CC_SYMBOLS = -DTARGET_LPC1768 -DTOOLCHAIN_GCC_CS -DNDEBUG
### PPRZ Datalink ###
PPRZ_DATALINK_PORT = Uart
PPRZ_DATALINK_DIR = .
include $(PPRZ_DATALINK_DIR)/datalink/pprz_datalink.mk
OBJECTS += $(PPRZ_DATALINK_OBJS)
CC_SYMBOLS += $(PPRZ_DATALINK_CFLAGS)
#####################
AS = $(GCC_BIN)arm-none-eabi-as
LD = $(GCC_BIN)arm-none-eabi-gcc
LD_FLAGS = -mcpu=cortex-m3 -mthumb -Wl,--gc-sections
LD_SYS_LIBS = -lstdc++ -lsupc++ -lm -lc -lgcc
OBJCOPY = $(GCC_BIN)arm-none-eabi-objcopy
all: $(PROJECT).bin
clean:
rm -f $(PROJECT).bin $(PROJECT).elf $(OBJECTS)
.s.o:
$(AS) $(CC_FLAGS) $(CC_SYMBOLS) -o $@ $<
.c.o:
$(CC) $(CC_FLAGS) $(CC_SYMBOLS) $(ONLY_C_FLAGS) $(INCLUDE_PATHS) -o $@ $<
.cpp.o:
$(CPP) $(CC_FLAGS) $(CC_SYMBOLS) $(ONLY_CPP_FLAGS) $(INCLUDE_PATHS) -o $@ $<
$(PROJECT).elf: $(OBJECTS) $(SYS_OBJECTS)
$(LD) $(LD_FLAGS) -T$(LINKER_SCRIPT) $(LIBRARY_PATHS) -o $@ $^ $(LIBRARIES) $(LD_SYS_LIBS) $(LIBRARIES) $(LD_SYS_LIBS)
$(PROJECT).bin: $(PROJECT).elf
$(OBJCOPY) -O binary $< $@
```
1 change: 0 additions & 1 deletion sw/airborne/subsystems/datalink/downlink.c
Expand Up @@ -27,7 +27,6 @@


#include "std.h"
#include "generated/airframe.h"

uint8_t downlink_nb_ovrn;
uint16_t downlink_nb_bytes;
Expand Down
12 changes: 12 additions & 0 deletions sw/airborne/subsystems/datalink/downlink.h
Expand Up @@ -30,6 +30,8 @@

#include <inttypes.h>

#ifndef PPRZ_DATALINK_EXPORT

#include "generated/modules.h"
#include "messages.h"
#include "generated/airframe.h" // AC_ID is required
Expand Down Expand Up @@ -64,6 +66,16 @@

#endif /** !SITL */

#else /* PPRZ_DATALINK_EXPORT defined */

#include "messages.h"
#include "pprz_transport.h"
#ifndef AC_ID
#define AC_ID 0
#endif

#endif

#ifndef DefaultChannel
#define DefaultChannel DOWNLINK_TRANSPORT
#endif
Expand Down
36 changes: 36 additions & 0 deletions sw/airborne/subsystems/datalink/pprz_datalink.mk
@@ -0,0 +1,36 @@
#
# Copyright (C) 2013 Gautier Hattenberger
#
# This file is part of paparazzi.
#
# paparazzi is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 2, or (at your option)
# any later version.
#
# paparazzi is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with paparazzi; see the file COPYING. If not, write to
# the Free Software Foundation, 59 Temple Place - Suite 330,
# Boston, MA 02111-1307, USA.
#

#
# PPRZ datalink makefile to include to your project
#
# define PPRZ_DATALINK_DIR variable to your extract folder
# define PPRZ_DATALINK_PORT variable to your UART port
# add PPRZ_DATALINK_CFLAGS to your CFLAGS
# and PPRZ_DATALINK_SRCS to your sources list
#

PPRZ_DATALINK_CFLAGS = -DPPRZ_DATALINK_EXPORT -I$(PPRZ_DATALINK_DIR)/datalink
PPRZ_DATALINK_CFLAGS += -DDOWNLINK -DDOWNLINK_DEVICE=$(PPRZ_DATALINK_PORT) -DPPRZ_UART=$(PPRZ_DATALINK_PORT) -DDOWNLINK_TRANSPORT=PprzTransport
PPRZ_DATALINK_CFLAGS += -DDATALINK=PPRZ
PPRZ_DATALINK_SRCS = $(PPRZ_DATALINK_DIR)/datalink/downlink.c $(PPRZ_DATALINK_DIR)/datalink/pprz_transport.c
PPRZ_DATALINK_OBJS = $(PPRZ_DATALINK_SRCS:.c=.o)

5 changes: 4 additions & 1 deletion sw/airborne/subsystems/datalink/pprz_transport.c
Expand Up @@ -21,8 +21,11 @@
*/

#include <inttypes.h>
#ifndef PPRZ_DATALINK_EXPORT
#include "subsystems/datalink/pprz_transport.h"
#include "mcu_periph/uart.h"
#else /* PPRZ_DATALINK_EXPORT defined */
#include "pprz_transport.h"
#endif

uint8_t ck_a, ck_b;

Expand Down
5 changes: 5 additions & 0 deletions sw/airborne/subsystems/datalink/pprz_transport.h
Expand Up @@ -43,8 +43,13 @@

#include <inttypes.h>
#include "std.h"
#ifndef PPRZ_DATALINK_EXPORT
#include "subsystems/datalink/datalink.h"
#include "subsystems/datalink/transport.h"
#else /* PPRZ_DATALINK_EXPORT defined */
#include "datalink.h"
#include "transport.h"
#endif

/* PPRZ Transport
* downlink macros
Expand Down

0 comments on commit 0a13cfe

Please sign in to comment.