mirror of
https://github.com/eclipse-mosquitto/mosquitto.git
synced 2026-02-05 10:40:05 +08:00
Initial contribution.
This commit is contained in:
39
.gitignore
vendored
Normal file
39
.gitignore
vendored
Normal file
@@ -0,0 +1,39 @@
|
||||
*.o
|
||||
*.exe
|
||||
*.db
|
||||
c/*.test
|
||||
cpp/*.test
|
||||
*.pyc
|
||||
|
||||
client/mosquitto_pub
|
||||
client/mosquitto_sub
|
||||
examples/mysql_log/mosquitto_mysql_log
|
||||
examples/temperature_conversion/mqtt_temperature_conversion
|
||||
man/mosquitto.8
|
||||
man/mosquitto-tls.7
|
||||
man/mosquitto.conf.5
|
||||
man/libmosquitto.3
|
||||
man/mosquitto_passwd.1
|
||||
man/mosquitto_pub.1
|
||||
man/mosquitto_sub.1
|
||||
man/mqtt.7
|
||||
src/db_dump/mosquitto_db_dump
|
||||
src/mosquitto
|
||||
src/mosquitto_passwd
|
||||
test/broker/broker.pid
|
||||
test/test_client
|
||||
test/fake_user
|
||||
test/msgsps_pub
|
||||
test/msgsps_sub
|
||||
test/msgsps_pub.dat
|
||||
test/msgsps_sub.dat
|
||||
test/broker/c/auth_plugin.so
|
||||
|
||||
lib/cpp/libmosquittopp.so*
|
||||
lib/libmosquitto.so*
|
||||
lib/libmosquitto.a
|
||||
|
||||
test/ssl/*.csr
|
||||
|
||||
build/
|
||||
dist/
|
||||
74
CMakeLists.txt
Normal file
74
CMakeLists.txt
Normal file
@@ -0,0 +1,74 @@
|
||||
# This is a cmake script.
|
||||
|
||||
set(CMAKE_LEGACY_CYGWIN_WIN32 0)
|
||||
|
||||
project(mosquitto)
|
||||
|
||||
cmake_minimum_required(VERSION 2.6)
|
||||
|
||||
set (VERSION 1.3.1)
|
||||
|
||||
if (WIN32)
|
||||
execute_process(COMMAND cmd /c echo %DATE% %TIME% OUTPUT_VARIABLE TIMESTAMP
|
||||
OUTPUT_STRIP_TRAILING_WHITESPACE)
|
||||
else (WIN32)
|
||||
execute_process(COMMAND date "+%F %T%z" OUTPUT_VARIABLE TIMESTAMP
|
||||
OUTPUT_STRIP_TRAILING_WHITESPACE)
|
||||
endif (WIN32)
|
||||
|
||||
add_definitions (-DCMAKE -DVERSION=\"${VERSION}\" -DTIMESTAMP=\"${TIMESTAMP}\")
|
||||
|
||||
if (WIN32)
|
||||
set (BINDIR .)
|
||||
set (SBINDIR .)
|
||||
set (SYSCONFDIR .)
|
||||
set (LIBDIR .)
|
||||
set (INCLUDEDIR include)
|
||||
set (DATAROOTDIR share)
|
||||
set (MANDIR man)
|
||||
set (SHAREDEST .)
|
||||
add_definitions("-D_CRT_SECURE_NO_WARNINGS")
|
||||
else (WIN32)
|
||||
set (BINDIR bin)
|
||||
set (SBINDIR sbin)
|
||||
if (${CMAKE_INSTALL_PREFIX} STREQUAL /usr)
|
||||
set (SYSCONFDIR /etc/mosquitto)
|
||||
else (${CMAKE_INSTALL_PREFIX} STREQUAL /usr)
|
||||
set (SYSCONFDIR etc/mosquitto)
|
||||
endif (${CMAKE_INSTALL_PREFIX} STREQUAL /usr)
|
||||
|
||||
set (LIBDIR lib${LIB_SUFFIX})
|
||||
set (INCLUDEDIR include)
|
||||
set (DATAROOTDIR share)
|
||||
set (MANDIR ${DATAROOTDIR}/man)
|
||||
set (SHAREDIR ${DATAROOTDIR}/mosquitto)
|
||||
endif (WIN32)
|
||||
|
||||
option(WITH_TLS
|
||||
"Include SSL/TLS support?" ON)
|
||||
option(WITH_TLS_PSK
|
||||
"Include TLS-PSK support (requires WITH_TLS)?" ON)
|
||||
if (${WITH_TLS} STREQUAL ON)
|
||||
find_package(OpenSSL REQUIRED)
|
||||
add_definitions("-DWITH_TLS")
|
||||
if (${WITH_TLS_PSK} STREQUAL ON)
|
||||
add_definitions("-DWITH_TLS_PSK")
|
||||
endif (${WITH_TLS_PSK} STREQUAL ON)
|
||||
else (${WITH_TLS} STREQUAL ON)
|
||||
set (OPENSSL_INCLUDE_DIR "")
|
||||
endif (${WITH_TLS} STREQUAL ON)
|
||||
|
||||
# ========================================
|
||||
# Include projects
|
||||
# ========================================
|
||||
|
||||
add_subdirectory(lib)
|
||||
add_subdirectory(client)
|
||||
add_subdirectory(src)
|
||||
add_subdirectory(man)
|
||||
|
||||
# ========================================
|
||||
# Install config file
|
||||
# ========================================
|
||||
|
||||
install(FILES mosquitto.conf aclfile.example pskfile.example pwfile.example DESTINATION ${SYSCONFDIR})
|
||||
1093
ChangeLog.txt
Normal file
1093
ChangeLog.txt
Normal file
File diff suppressed because it is too large
Load Diff
2
LICENSE.txt
Normal file
2
LICENSE.txt
Normal file
@@ -0,0 +1,2 @@
|
||||
This project is dual licensed under the Eclipse Public License 1.0 and the
|
||||
Eclipse Distribution License 1.0 as described in the epl-v10 and edl-v10 files.
|
||||
70
Makefile
Normal file
70
Makefile
Normal file
@@ -0,0 +1,70 @@
|
||||
include config.mk
|
||||
|
||||
DIRS=lib client src
|
||||
DOCDIRS=man
|
||||
DISTDIRS=man
|
||||
|
||||
.PHONY : all mosquitto docs binary clean reallyclean test install uninstall dist sign copy
|
||||
|
||||
all : mosquitto docs
|
||||
|
||||
docs :
|
||||
set -e; for d in ${DOCDIRS}; do $(MAKE) -C $${d}; done
|
||||
|
||||
binary : mosquitto
|
||||
|
||||
mosquitto :
|
||||
set -e; for d in ${DIRS}; do $(MAKE) -C $${d}; done
|
||||
|
||||
clean :
|
||||
set -e; for d in ${DIRS}; do $(MAKE) -C $${d} clean; done
|
||||
set -e; for d in ${DOCDIRS}; do $(MAKE) -C $${d} clean; done
|
||||
$(MAKE) -C test clean
|
||||
|
||||
reallyclean :
|
||||
set -e; for d in ${DIRS}; do $(MAKE) -C $${d} reallyclean; done
|
||||
set -e; for d in ${DOCDIRS}; do $(MAKE) -C $${d} reallyclean; done
|
||||
$(MAKE) -C test reallyclean
|
||||
-rm -f *.orig
|
||||
|
||||
test : mosquitto
|
||||
$(MAKE) -C test test
|
||||
|
||||
install : mosquitto
|
||||
set -e; for d in ${DIRS}; do $(MAKE) -C $${d} install; done
|
||||
set -e; for d in ${DOCDIRS}; do $(MAKE) -C $${d} install; done
|
||||
$(INSTALL) -d ${DESTDIR}/etc/mosquitto
|
||||
$(INSTALL) -m 644 mosquitto.conf ${DESTDIR}/etc/mosquitto/mosquitto.conf.example
|
||||
$(INSTALL) -m 644 aclfile.example ${DESTDIR}/etc/mosquitto/aclfile.example
|
||||
$(INSTALL) -m 644 pwfile.example ${DESTDIR}/etc/mosquitto/pwfile.example
|
||||
$(INSTALL) -m 644 pskfile.example ${DESTDIR}/etc/mosquitto/pskfile.example
|
||||
|
||||
uninstall :
|
||||
set -e; for d in ${DIRS}; do $(MAKE) -C $${d} uninstall; done
|
||||
rm -f ${DESTDIR}/etc/mosquitto/mosquitto.conf
|
||||
rm -f ${DESTDIR}/etc/mosquitto/aclfile.example
|
||||
rm -f ${DESTDIR}/etc/mosquitto/pwfile.example
|
||||
rm -f ${DESTDIR}/etc/mosquitto/pskfile.example
|
||||
|
||||
dist : reallyclean
|
||||
set -e; for d in ${DISTDIRS}; do $(MAKE) -C $${d} dist; done
|
||||
|
||||
echo $$(hg log -r . --template "{node}") > changeset
|
||||
mkdir -p dist/mosquitto-${VERSION}
|
||||
cp -r client changeset examples installer lib logo man misc security service src test ChangeLog.txt CMakeLists.txt LICENSE.txt LICENSE-3rd-party.txt Makefile compiling.txt config.h config.mk readme.txt readme-windows.txt mosquitto.conf aclfile.example pskfile.example pwfile.example dist/mosquitto-${VERSION}/
|
||||
cd dist; tar -zcf mosquitto-${VERSION}.tar.gz mosquitto-${VERSION}/
|
||||
set -e; for m in man/*.xml; \
|
||||
do \
|
||||
hfile=$$(echo $${m} | sed -e 's#man/\(.*\)\.xml#\1#' | sed -e 's/\./-/g'); \
|
||||
$(XSLTPROC) $(DB_HTML_XSL) $${m} > dist/$${hfile}.html; \
|
||||
done
|
||||
|
||||
|
||||
sign : dist
|
||||
cd dist; gpg --detach-sign -a mosquitto-${VERSION}.tar.gz
|
||||
|
||||
copy : sign
|
||||
cd dist; scp mosquitto-${VERSION}.tar.gz mosquitto-${VERSION}.tar.gz.asc mosquitto:site/mosquitto.org/files/source/
|
||||
cd dist; scp *.html mosquitto:site/mosquitto.org/man/
|
||||
scp ChangeLog.txt mosquitto:site/mosquitto.org/
|
||||
|
||||
57
THANKS.txt
Normal file
57
THANKS.txt
Normal file
@@ -0,0 +1,57 @@
|
||||
These people have reported bugs / provided patches / done something else to aid
|
||||
the mosquitto project. Thanks to you all!
|
||||
|
||||
If you think I've missed you off the list, please rest assured that it wasn't
|
||||
intentional and get in touch and I'll fix it.
|
||||
|
||||
Adam Rudd
|
||||
Andrew Elwell
|
||||
Andy Piper
|
||||
Andy Stanford-Clark
|
||||
Bart Van Der Meerssche
|
||||
Ben Tobin
|
||||
Brad Stancel
|
||||
Chris Willing
|
||||
Craig Hollabaugh
|
||||
Dan Anderson
|
||||
Dariusz Suchojad
|
||||
David Huang
|
||||
David Monro
|
||||
Dirk O. Kaar
|
||||
Dominik Obermaier
|
||||
Dominik Zajac
|
||||
Ed Morris
|
||||
Frank Hansen
|
||||
Gary Koh
|
||||
Joan Zapata
|
||||
Karl Palsson
|
||||
Larry Lendo
|
||||
Martin Assarsson
|
||||
Marty Lee
|
||||
Matt Daubney
|
||||
Michael C
|
||||
Michael Frisch
|
||||
Michael Rushton
|
||||
Mike Bush
|
||||
Neil Bothwick
|
||||
Nicholas Humfrey
|
||||
Nicholas O'Leary
|
||||
Nithin Kumar
|
||||
Paul Diston
|
||||
Peter George
|
||||
Rob Pridham
|
||||
Robin Gingras
|
||||
Roland de Boo
|
||||
Sebastian Kroll
|
||||
Sharon Ben-Asher
|
||||
sskaje
|
||||
Stefan Hudelmaier
|
||||
Stefano Costa
|
||||
Stephen Woods
|
||||
Steven Lougheed
|
||||
Thomas Hilbig
|
||||
Tobias Assarsson
|
||||
Toby Jaffey
|
||||
Vicente Ruiz
|
||||
Wayne Ingram
|
||||
Yuvraaj Kelkar
|
||||
9
aclfile.example
Normal file
9
aclfile.example
Normal file
@@ -0,0 +1,9 @@
|
||||
# This affects access control for clients with no username.
|
||||
topic read $SYS/#
|
||||
|
||||
# This only affects clients with username "roger".
|
||||
user roger
|
||||
topic foo/bar
|
||||
|
||||
# This affects all clients.
|
||||
pattern write $SYS/broker/connection/%c/state
|
||||
12
client/CMakeLists.txt
Normal file
12
client/CMakeLists.txt
Normal file
@@ -0,0 +1,12 @@
|
||||
include_directories(${mosquitto_SOURCE_DIR}/lib
|
||||
${STDBOOL_H_PATH} ${STDINT_H_PATH})
|
||||
link_directories(${mosquitto_BINARY_DIR}/lib)
|
||||
|
||||
add_executable(mosquitto_pub pub_client.c)
|
||||
add_executable(mosquitto_sub sub_client.c)
|
||||
|
||||
target_link_libraries(mosquitto_pub mosquitto)
|
||||
target_link_libraries(mosquitto_sub mosquitto)
|
||||
|
||||
install(TARGETS mosquitto_pub RUNTIME DESTINATION ${BINDIR} LIBRARY DESTINATION ${LIBDIR})
|
||||
install(TARGETS mosquitto_sub RUNTIME DESTINATION ${BINDIR} LIBRARY DESTINATION ${LIBDIR})
|
||||
34
client/Makefile
Normal file
34
client/Makefile
Normal file
@@ -0,0 +1,34 @@
|
||||
include ../config.mk
|
||||
|
||||
.PHONY: all install uninstall reallyclean clean
|
||||
|
||||
all : mosquitto_pub mosquitto_sub
|
||||
|
||||
mosquitto_pub : pub_client.o ../lib/libmosquitto.so.${SOVERSION}
|
||||
${CC} $< -o $@ ${CLIENT_LDFLAGS}
|
||||
|
||||
mosquitto_sub : sub_client.o ../lib/libmosquitto.so.${SOVERSION}
|
||||
${CC} $< -o $@ ${CLIENT_LDFLAGS}
|
||||
|
||||
pub_client.o : pub_client.c ../lib/libmosquitto.so.${SOVERSION}
|
||||
${CC} -c $< -o $@ ${CLIENT_CFLAGS}
|
||||
|
||||
sub_client.o : sub_client.c ../lib/libmosquitto.so.${SOVERSION}
|
||||
${CC} -c $< -o $@ ${CLIENT_CFLAGS}
|
||||
|
||||
../lib/libmosquitto.so.${SOVERSION} :
|
||||
$(MAKE) -C ../lib
|
||||
|
||||
install : all
|
||||
$(INSTALL) -d ${DESTDIR}$(prefix)/bin
|
||||
$(INSTALL) -s mosquitto_pub ${DESTDIR}${prefix}/bin/mosquitto_pub
|
||||
$(INSTALL) -s mosquitto_sub ${DESTDIR}${prefix}/bin/mosquitto_sub
|
||||
|
||||
uninstall :
|
||||
-rm -f ${DESTDIR}${prefix}/bin/mosquitto_pub
|
||||
-rm -f ${DESTDIR}${prefix}/bin/mosquitto_sub
|
||||
|
||||
reallyclean : clean
|
||||
|
||||
clean :
|
||||
-rm -f *.o mosquitto_pub mosquitto_sub
|
||||
785
client/pub_client.c
Normal file
785
client/pub_client.c
Normal file
File diff suppressed because it is too large
Load Diff
650
client/sub_client.c
Normal file
650
client/sub_client.c
Normal file
File diff suppressed because it is too large
Load Diff
17
compiling.txt
Normal file
17
compiling.txt
Normal file
@@ -0,0 +1,17 @@
|
||||
The following packages are required for mosquitto:
|
||||
|
||||
* tcp-wrappers (optional, package name libwrap0-dev)
|
||||
* openssl (version 1.0.0 or greater if TLS-PSK support is needed)
|
||||
* On Windows, the Redhat pthreads library is required if threading support is
|
||||
to be included.
|
||||
|
||||
To compile, run "make", but also see the file config.mk for more details on the
|
||||
various options that can be compiled in.
|
||||
|
||||
Where possible use the Makefiles to compile. This is particularly relevant for
|
||||
the client libraries as symbol information will be included. Use cmake to
|
||||
compile on Windows or Mac.
|
||||
|
||||
If you have any questions, problems or suggestions (particularly related to
|
||||
installing on a more unusual device like a plug-computer) then please get in
|
||||
touch using the details in readme.txt.
|
||||
19
config.h
Normal file
19
config.h
Normal file
@@ -0,0 +1,19 @@
|
||||
/* ============================================================
|
||||
* Control compile time options.
|
||||
* ============================================================
|
||||
*
|
||||
* Compile time options have moved to config.mk.
|
||||
*/
|
||||
|
||||
|
||||
/* ============================================================
|
||||
* Compatibility defines
|
||||
*
|
||||
* Generally for Windows native support.
|
||||
* ============================================================ */
|
||||
#ifdef WIN32
|
||||
#define snprintf sprintf_s
|
||||
#define strcasecmp strcmpi
|
||||
#define strtok_r strtok_s
|
||||
#define strerror_r(e, b, l) strerror_s(b, l, e)
|
||||
#endif
|
||||
218
config.mk
Normal file
218
config.mk
Normal file
@@ -0,0 +1,218 @@
|
||||
# =============================================================================
|
||||
# User configuration section.
|
||||
#
|
||||
# Largely, these are options that are designed to make mosquitto run more
|
||||
# easily in restrictive environments by removing features.
|
||||
#
|
||||
# Modify the variable below to enable/disable features.
|
||||
#
|
||||
# Can also be overriden at the command line, e.g.:
|
||||
#
|
||||
# make WITH_TLS=no
|
||||
# =============================================================================
|
||||
|
||||
# Uncomment to compile the broker with tcpd/libwrap support.
|
||||
#WITH_WRAP:=yes
|
||||
|
||||
# Comment out to disable SSL/TLS support in the broker and client.
|
||||
# Disabling this will also mean that passwords must be stored in plain text. It
|
||||
# is strongly recommended that you only disable WITH_TLS if you are not using
|
||||
# password authentication at all.
|
||||
WITH_TLS:=yes
|
||||
|
||||
# Comment out to disable TLS/PSK support in the broker and client. Requires
|
||||
# WITH_TLS=yes.
|
||||
# This must be disabled if using openssl < 1.0.
|
||||
WITH_TLS_PSK:=yes
|
||||
|
||||
# Comment out to disable client client threading support.
|
||||
WITH_THREADING:=yes
|
||||
|
||||
# Uncomment to compile the broker with strict protocol support. This means that
|
||||
# both the client library and the broker will be very strict about protocol
|
||||
# compliance on incoming data. Neither of them will return an error on
|
||||
# incorrect "remaining length" values if this is commented out. The old
|
||||
# behaviour (prior to 0.12) is equivalent to compiling with
|
||||
# WITH_STRICT_PROTOCOL defined and means that clients will be immediately
|
||||
# disconnected from the broker on non-compliance.
|
||||
#WITH_STRICT_PROTOCOL:=yes
|
||||
|
||||
# Comment out to remove bridge support from the broker. This allow the broker
|
||||
# to connect to other brokers and subscribe/publish to topics. You probably
|
||||
# want to leave this included unless you want to save a very small amount of
|
||||
# memory size and CPU time.
|
||||
WITH_BRIDGE:=yes
|
||||
|
||||
# Comment out to remove persistent database support from the broker. This
|
||||
# allows the broker to store retained messages and durable subscriptions to a
|
||||
# file periodically and on shutdown. This is usually desirable (and is
|
||||
# suggested by the MQTT spec), but it can be disabled if required.
|
||||
WITH_PERSISTENCE:=yes
|
||||
|
||||
# Comment out to remove memory tracking support from the broker. If disabled,
|
||||
# mosquitto won't track heap memory usage nor export '$SYS/broker/heap/current
|
||||
# size', but will use slightly less memory and CPU time.
|
||||
WITH_MEMORY_TRACKING:=yes
|
||||
|
||||
# Compile with database upgrading support? If disabled, mosquitto won't
|
||||
# automatically upgrade old database versions.
|
||||
# Not currently supported.
|
||||
#WITH_DB_UPGRADE:=yes
|
||||
|
||||
# Comment out to remove publishing of the $SYS topic hierarchy containing
|
||||
# information about the broker state.
|
||||
WITH_SYS_TREE:=yes
|
||||
|
||||
# Build with Python module. Comment out if Python is not installed, or required
|
||||
# Python modules are not available.
|
||||
WITH_PYTHON:=yes
|
||||
|
||||
# Build with SRV lookup support.
|
||||
WITH_SRV:=yes
|
||||
|
||||
# =============================================================================
|
||||
# End of user configuration
|
||||
# =============================================================================
|
||||
|
||||
|
||||
# Also bump lib/mosquitto.h, lib/python/setup.py, CMakeLists.txt,
|
||||
# installer/mosquitto.nsi, installer/mosquitto-cygwin.nsi
|
||||
VERSION=1.3.1
|
||||
TIMESTAMP:=$(shell date "+%F %T%z")
|
||||
|
||||
# Client library SO version. Bump if incompatible API/ABI changes are made.
|
||||
SOVERSION=1
|
||||
|
||||
# Man page generation requires xsltproc and docbook-xsl
|
||||
XSLTPROC=xsltproc
|
||||
# For html generation
|
||||
DB_HTML_XSL=man/html.xsl
|
||||
|
||||
#MANCOUNTRIES=en_GB
|
||||
|
||||
UNAME:=$(shell uname -s)
|
||||
ifeq ($(UNAME),SunOS)
|
||||
ifeq ($(CC),cc)
|
||||
CFLAGS?=-O
|
||||
else
|
||||
CFLAGS?=-Wall -ggdb -O2
|
||||
endif
|
||||
else
|
||||
CFLAGS?=-Wall -ggdb -O2
|
||||
endif
|
||||
|
||||
LIB_CFLAGS:=${CFLAGS} ${CPPFLAGS} -I. -I.. -I../lib
|
||||
LIB_CXXFLAGS:=$(LIB_CFLAGS) ${CPPFLAGS}
|
||||
LIB_LDFLAGS:=${LDFLAGS}
|
||||
|
||||
BROKER_CFLAGS:=${LIB_CFLAGS} ${CPPFLAGS} -DVERSION="\"${VERSION}\"" -DTIMESTAMP="\"${TIMESTAMP}\"" -DWITH_BROKER
|
||||
CLIENT_CFLAGS:=${CFLAGS} ${CPPFLAGS} -I../lib -DVERSION="\"${VERSION}\""
|
||||
|
||||
ifeq ($(UNAME),FreeBSD)
|
||||
BROKER_LIBS:=-lm
|
||||
else
|
||||
BROKER_LIBS:=-ldl -lm
|
||||
endif
|
||||
LIB_LIBS:=
|
||||
PASSWD_LIBS:=
|
||||
|
||||
ifeq ($(UNAME),Linux)
|
||||
BROKER_LIBS:=$(BROKER_LIBS) -lrt
|
||||
LIB_LIBS:=$(LIB_LIBS) -lrt
|
||||
endif
|
||||
|
||||
CLIENT_LDFLAGS:=$(LDFLAGS) -L../lib ../lib/libmosquitto.so.${SOVERSION}
|
||||
|
||||
ifeq ($(UNAME),SunOS)
|
||||
ifeq ($(CC),cc)
|
||||
LIB_CFLAGS:=$(LIB_CFLAGS) -xc99 -KPIC
|
||||
else
|
||||
LIB_CFLAGS:=$(LIB_CFLAGS) -fPIC
|
||||
endif
|
||||
|
||||
ifeq ($(CXX),CC)
|
||||
LIB_CXXFLAGS:=$(LIB_CXXFLAGS) -KPIC
|
||||
else
|
||||
LIB_CXXFLAGS:=$(LIB_CXXFLAGS) -fPIC
|
||||
endif
|
||||
else
|
||||
LIB_CFLAGS:=$(LIB_CFLAGS) -fPIC
|
||||
LIB_CXXFLAGS:=$(LIB_CXXFLAGS) -fPIC
|
||||
endif
|
||||
|
||||
ifneq ($(UNAME),SunOS)
|
||||
LIB_LDFLAGS:=$(LIB_LDFLAGS) -Wl,--version-script=linker.version -Wl,-soname,libmosquitto.so.$(SOVERSION)
|
||||
endif
|
||||
|
||||
ifeq ($(UNAME),QNX)
|
||||
BROKER_LIBS:=$(BROKER_LIBS) -lsocket
|
||||
LIB_LIBS:=$(LIB_LIBS) -lsocket
|
||||
endif
|
||||
|
||||
ifeq ($(WITH_WRAP),yes)
|
||||
BROKER_LIBS:=$(BROKER_LIBS) -lwrap
|
||||
BROKER_CFLAGS:=$(BROKER_CFLAGS) -DWITH_WRAP
|
||||
endif
|
||||
|
||||
ifeq ($(WITH_TLS),yes)
|
||||
BROKER_LIBS:=$(BROKER_LIBS) -lssl -lcrypto
|
||||
LIB_LIBS:=$(LIB_LIBS) -lssl -lcrypto
|
||||
BROKER_CFLAGS:=$(BROKER_CFLAGS) -DWITH_TLS
|
||||
LIB_CFLAGS:=$(LIB_CFLAGS) -DWITH_TLS
|
||||
PASSWD_LIBS:=-lcrypto
|
||||
CLIENT_CFLAGS:=$(CLIENT_CFLAGS) -DWITH_TLS
|
||||
|
||||
ifeq ($(WITH_TLS_PSK),yes)
|
||||
BROKER_CFLAGS:=$(BROKER_CFLAGS) -DWITH_TLS_PSK
|
||||
LIB_CFLAGS:=$(LIB_CFLAGS) -DWITH_TLS_PSK
|
||||
CLIENT_CFLAGS:=$(CLIENT_CFLAGS) -DWITH_TLS_PSK
|
||||
endif
|
||||
endif
|
||||
|
||||
ifeq ($(WITH_THREADING),yes)
|
||||
LIB_LIBS:=$(LIB_LIBS) -lpthread
|
||||
LIB_CFLAGS:=$(LIB_CFLAGS) -DWITH_THREADING
|
||||
endif
|
||||
|
||||
ifeq ($(WITH_STRICT_PROTOCOL),yes)
|
||||
LIB_CFLAGS:=$(LIB_CFLAGS) -DWITH_STRICT_PROTOCOL
|
||||
BROKER_CFLAGS:=$(BROKER_CFLAGS) -DWITH_STRICT_PROTOCOL
|
||||
endif
|
||||
|
||||
ifeq ($(WITH_BRIDGE),yes)
|
||||
BROKER_CFLAGS:=$(BROKER_CFLAGS) -DWITH_BRIDGE
|
||||
endif
|
||||
|
||||
ifeq ($(WITH_PERSISTENCE),yes)
|
||||
BROKER_CFLAGS:=$(BROKER_CFLAGS) -DWITH_PERSISTENCE
|
||||
endif
|
||||
|
||||
ifeq ($(WITH_MEMORY_TRACKING),yes)
|
||||
ifneq ($(UNAME),SunOS)
|
||||
BROKER_CFLAGS:=$(BROKER_CFLAGS) -DWITH_MEMORY_TRACKING
|
||||
endif
|
||||
endif
|
||||
|
||||
#ifeq ($(WITH_DB_UPGRADE),yes)
|
||||
# BROKER_CFLAGS:=$(BROKER_CFLAGS) -DWITH_DB_UPGRADE
|
||||
#endif
|
||||
|
||||
ifeq ($(WITH_SYS_TREE),yes)
|
||||
BROKER_CFLAGS:=$(BROKER_CFLAGS) -DWITH_SYS_TREE
|
||||
endif
|
||||
|
||||
ifeq ($(WITH_SRV),yes)
|
||||
LIB_CFLAGS:=$(LIB_CFLAGS) -DWITH_SRV
|
||||
LIB_LIBS:=$(LIB_LIBS) -lcares
|
||||
endif
|
||||
|
||||
ifeq ($(UNAME),SunOS)
|
||||
BROKER_LIBS:=$(BROKER_LIBS) -lsocket -lnsl
|
||||
LIB_LIBS:=$(LIB_LIBS) -lsocket -lnsl
|
||||
endif
|
||||
|
||||
|
||||
INSTALL?=install
|
||||
prefix=/usr/local
|
||||
mandir=${prefix}/share/man
|
||||
localedir=${prefix}/share/locale
|
||||
43
doc/historical/old-regex.txt
Normal file
43
doc/historical/old-regex.txt
Normal file
@@ -0,0 +1,43 @@
|
||||
This is the description of the regex used previously for topic/subscription
|
||||
matching. It is reproduced here for posterity.
|
||||
|
||||
When a message is ready to be published at the broker, we need to check all
|
||||
of the subscriptions to see which ones the message should be sent to. This
|
||||
would be easy without wildcards, but requires a bit more work with them.
|
||||
|
||||
The regex used to do the matching is of the form below for a topic of a/b/c:
|
||||
|
||||
^(?:(?:(a|\+)(?!$))(?:(?:/(?:(b|\+)(?!$)))(?:(?:/(?:c|\+))|/#)?|/#)?|#)$
|
||||
|
||||
In general, we're matching (a or +) followed by (the next levels of
|
||||
hierarchy or #).
|
||||
More specifically, all the levels of hierarchy must match, unless the last
|
||||
level is #.
|
||||
|
||||
^(?: # Must start at beginning of string
|
||||
(?: # (Level 1 hierarchy)
|
||||
(a|\+)(?!$) # Match a or +, but only if not EOL.
|
||||
) # AND
|
||||
(?:
|
||||
(?: # (Level 2 hierarchy)
|
||||
/ # Match /
|
||||
(?: # AND
|
||||
(b|\+)(?!$) # Match b or +, but only if not EOL.
|
||||
)
|
||||
) # AND
|
||||
(?:
|
||||
(?: # (Level 3 hierarchy)
|
||||
/ # Match /
|
||||
(?: # AND
|
||||
c|\+ # Match c or +.
|
||||
)
|
||||
)
|
||||
| # OR (instead of level 3)
|
||||
/# # Match /# at level 3
|
||||
)? # Level 3 exist 1/0 times
|
||||
| # OR (instead of level 2)
|
||||
/# # Match /# at level 2
|
||||
)? # Level 2 exist 1/0 times
|
||||
| # OR (instead of level 1)
|
||||
# # Match # at level 1
|
||||
)$ # Must end on EOL.
|
||||
7
doc/historical/topic-match.kds
Normal file
7
doc/historical/topic-match.kds
Normal file
@@ -0,0 +1,7 @@
|
||||
S'^(?:(?:(a|\\+)(?!$))(?:(?:/(?:(b|\\+)(?!$)))(?:(?:/(?:c|\\+))|/#)?|/#)?|#)$'
|
||||
p1
|
||||
.S'a/#\na/b/c\na/b/+\na/b\na/+\n+\n+/b\n+/+/+\n+/b/c\na/c'
|
||||
p2
|
||||
.I8
|
||||
.S''
|
||||
.
|
||||
31
edl-v10
Normal file
31
edl-v10
Normal file
@@ -0,0 +1,31 @@
|
||||
Eclipse Distribution License - v 1.0
|
||||
|
||||
Copyright (c) 2007, Eclipse Foundation, Inc. and its licensors.
|
||||
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this
|
||||
list of conditions and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Eclipse Foundation, Inc. nor the names of its
|
||||
contributors may be used to endorse or promote products derived from this
|
||||
software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR
|
||||
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
221
epl-v10
Normal file
221
epl-v10
Normal file
@@ -0,0 +1,221 @@
|
||||
Eclipse Public License - v 1.0
|
||||
|
||||
THE ACCOMPANYING PROGRAM IS PROVIDED UNDER THE TERMS OF THIS ECLIPSE PUBLIC
|
||||
LICENSE ("AGREEMENT"). ANY USE, REPRODUCTION OR DISTRIBUTION OF THE PROGRAM
|
||||
CONSTITUTES RECIPIENT'S ACCEPTANCE OF THIS AGREEMENT.
|
||||
|
||||
|
||||
1. DEFINITIONS
|
||||
|
||||
"Contribution" means:
|
||||
a) in the case of the initial Contributor, the initial code and
|
||||
documentation distributed under this Agreement, and
|
||||
|
||||
b) in the case of each subsequent Contributor:
|
||||
|
||||
i) changes to the Program, and
|
||||
ii) additions to the Program;
|
||||
|
||||
where such changes and/or additions to the Program originate from and are
|
||||
distributed by that particular Contributor. A Contribution 'originates' from a
|
||||
Contributor if it was added to the Program by such Contributor itself or anyone
|
||||
acting on such Contributor's behalf. Contributions do not include additions to
|
||||
the Program which: (i) are separate modules of software distributed in
|
||||
conjunction with the Program under their own license agreement, and (ii) are
|
||||
not derivative works of the Program.
|
||||
|
||||
"Contributor" means any person or entity that distributes the Program.
|
||||
|
||||
"Licensed Patents " mean patent claims licensable by a Contributor which are
|
||||
necessarily infringed by the use or sale of its Contribution alone or when
|
||||
combined with the Program.
|
||||
|
||||
"Program" means the Contributions distributed in accordance with this Agreement.
|
||||
|
||||
"Recipient" means anyone who receives the Program under this Agreement,
|
||||
including all Contributors.
|
||||
|
||||
|
||||
2. GRANT OF RIGHTS
|
||||
|
||||
a) Subject to the terms of this Agreement, each Contributor hereby grants
|
||||
Recipient a non-exclusive, worldwide, royalty-free copyright license to
|
||||
reproduce, prepare derivative works of, publicly display, publicly
|
||||
perform, distribute and sublicense the Contribution of such Contributor,
|
||||
if any, and such derivative works, in source code and object code form.
|
||||
|
||||
b) Subject to the terms of this Agreement, each Contributor hereby grants
|
||||
Recipient a non-exclusive, worldwide, royalty-free patent license under
|
||||
Licensed Patents to make, use, sell, offer to sell, import and otherwise
|
||||
transfer the Contribution of such Contributor, if any, in source code and
|
||||
object code form. This patent license shall apply to the combination of the
|
||||
Contribution and the Program if, at the time the Contribution is added by the
|
||||
Contributor, such addition of the Contribution causes such combination to be
|
||||
covered by the Licensed Patents. The patent license shall not apply to any
|
||||
other combinations which include the Contribution. No hardware per se is
|
||||
licensed hereunder.
|
||||
|
||||
c) Recipient understands that although each Contributor grants the licenses
|
||||
to its Contributions set forth herein, no assurances are provided by any
|
||||
Contributor that the Program does not infringe the patent or other
|
||||
intellectual property rights of any other entity. Each Contributor disclaims
|
||||
any liability to Recipient for claims brought by any other entity based on
|
||||
infringement of intellectual property rights or otherwise. As a condition to
|
||||
exercising the rights and licenses granted hereunder, each Recipient hereby
|
||||
assumes sole responsibility to secure any other intellectual property rights
|
||||
needed, if any. For example, if a third party patent license is required to
|
||||
allow Recipient to distribute the Program, it is Recipient's responsibility
|
||||
to acquire that license before distributing the Program.
|
||||
|
||||
d) Each Contributor represents that to its knowledge it has sufficient
|
||||
copyright rights in its Contribution, if any, to grant the copyright license
|
||||
set forth in this Agreement.
|
||||
|
||||
|
||||
3. REQUIREMENTS
|
||||
|
||||
A Contributor may choose to distribute the Program in object code form under
|
||||
its own license agreement, provided that:
|
||||
|
||||
a) it complies with the terms and conditions of this Agreement; and
|
||||
|
||||
b) its license agreement:
|
||||
|
||||
i) effectively disclaims on behalf of all Contributors all warranties and
|
||||
conditions, express and implied, including warranties or conditions of
|
||||
title and non-infringement, and implied warranties or conditions of
|
||||
merchantability and fitness for a particular purpose;
|
||||
|
||||
ii) effectively excludes on behalf of all Contributors all liability for
|
||||
damages, including direct, indirect, special, incidental and consequential
|
||||
damages, such as lost profits;
|
||||
|
||||
iii) states that any provisions which differ from this Agreement are offered
|
||||
by that Contributor alone and not by any other party; and
|
||||
|
||||
iv) states that source code for the Program is available from such
|
||||
Contributor, and informs licensees how to obtain it in a reasonable manner
|
||||
on or through a medium customarily used for software exchange.
|
||||
|
||||
When the Program is made available in source code form:
|
||||
|
||||
a) it must be made available under this Agreement; and
|
||||
|
||||
b) a copy of this Agreement must be included with each copy of the Program.
|
||||
|
||||
Contributors may not remove or alter any copyright notices contained within
|
||||
the Program.
|
||||
|
||||
Each Contributor must identify itself as the originator of its Contribution,
|
||||
if any, in a manner that reasonably allows subsequent Recipients to identify
|
||||
the originator of the Contribution.
|
||||
|
||||
|
||||
4. COMMERCIAL DISTRIBUTION
|
||||
|
||||
Commercial distributors of software may accept certain responsibilities with
|
||||
respect to end users, business partners and the like. While this license is
|
||||
intended to facilitate the commercial use of the Program, the Contributor who
|
||||
includes the Program in a commercial product offering should do so in a
|
||||
manner which does not create potential liability for other Contributors.
|
||||
Therefore, if a Contributor includes the Program in a commercial product
|
||||
offering, such Contributor ("Commercial Contributor") hereby agrees to defend
|
||||
and indemnify every other Contributor ("Indemnified Contributor") against any
|
||||
losses, damages and costs (collectively "Losses") arising from claims,
|
||||
lawsuits and other legal actions brought by a third party against the
|
||||
Indemnified Contributor to the extent caused by the acts or omissions of such
|
||||
Commercial Contributor in connection with its distribution of the Program in
|
||||
a commercial product offering. The obligations in this section do not apply
|
||||
to any claims or Losses relating to any actual or alleged intellectual
|
||||
property infringement. In order to qualify, an Indemnified Contributor must:
|
||||
a) promptly notify the Commercial Contributor in writing of such claim, and
|
||||
b) allow the Commercial Contributor to control, and cooperate with the
|
||||
Commercial Contributor in, the defense and any related settlement
|
||||
negotiations. The Indemnified Contributor may participate in any such claim
|
||||
at its own expense.
|
||||
|
||||
For example, a Contributor might include the Program in a commercial product
|
||||
offering, Product X. That Contributor is then a Commercial Contributor. If
|
||||
that Commercial Contributor then makes performance claims, or offers
|
||||
warranties related to Product X, those performance claims and warranties are
|
||||
such Commercial Contributor's responsibility alone. Under this section, the
|
||||
Commercial Contributor would have to defend claims against the other
|
||||
Contributors related to those performance claims and warranties, and if a
|
||||
court requires any other Contributor to pay any damages as a result, the
|
||||
Commercial Contributor must pay those damages.
|
||||
|
||||
|
||||
5. NO WARRANTY
|
||||
|
||||
EXCEPT AS EXPRESSLY SET FORTH IN THIS AGREEMENT, THE PROGRAM IS PROVIDED ON
|
||||
AN "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, EITHER
|
||||
EXPRESS OR IMPLIED INCLUDING, WITHOUT LIMITATION, ANY WARRANTIES OR
|
||||
CONDITIONS OF TITLE, NON-INFRINGEMENT, MERCHANTABILITY OR FITNESS FOR A
|
||||
PARTICULAR PURPOSE. Each Recipient is solely responsible for determining the
|
||||
appropriateness of using and distributing the Program and assumes all risks
|
||||
associated with its exercise of rights under this Agreement , including but
|
||||
not limited to the risks and costs of program errors, compliance with
|
||||
applicable laws, damage to or loss of data, programs or equipment, and
|
||||
unavailability or interruption of operations.
|
||||
|
||||
|
||||
6. DISCLAIMER OF LIABILITY
|
||||
|
||||
EXCEPT AS EXPRESSLY SET FORTH IN THIS AGREEMENT, NEITHER RECIPIENT NOR ANY
|
||||
CONTRIBUTORS SHALL HAVE ANY LIABILITY FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
||||
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING WITHOUT LIMITATION
|
||||
LOST PROFITS), HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
ARISING IN ANY WAY OUT OF THE USE OR DISTRIBUTION OF THE PROGRAM OR THE
|
||||
EXERCISE OF ANY RIGHTS GRANTED HEREUNDER, EVEN IF ADVISED OF THE POSSIBILITY
|
||||
OF SUCH DAMAGES.
|
||||
|
||||
|
||||
7. GENERAL
|
||||
|
||||
If any provision of this Agreement is invalid or unenforceable under
|
||||
applicable law, it shall not affect the validity or enforceability of the
|
||||
remainder of the terms of this Agreement, and without further action by the
|
||||
parties hereto, such provision shall be reformed to the minimum extent
|
||||
necessary to make such provision valid and enforceable.
|
||||
|
||||
If Recipient institutes patent litigation against any entity (including a
|
||||
cross-claim or counterclaim in a lawsuit) alleging that the Program itself
|
||||
(excluding combinations of the Program with other software or hardware)
|
||||
infringes such Recipient's patent(s), then such Recipient's rights granted
|
||||
under Section 2(b) shall terminate as of the date such litigation is filed.
|
||||
|
||||
All Recipient's rights under this Agreement shall terminate if it fails to
|
||||
comply with any of the material terms or conditions of this Agreement and
|
||||
does not cure such failure in a reasonable period of time after becoming
|
||||
aware of such noncompliance. If all Recipient's rights under this Agreement
|
||||
terminate, Recipient agrees to cease use and distribution of the Program as
|
||||
soon as reasonably practicable. However, Recipient's obligations under this
|
||||
Agreement and any licenses granted by Recipient relating to the Program shall
|
||||
continue and survive.
|
||||
|
||||
Everyone is permitted to copy and distribute copies of this Agreement, but in
|
||||
order to avoid inconsistency the Agreement is copyrighted and may only be
|
||||
modified in the following manner. The Agreement Steward reserves the right to
|
||||
publish new versions (including revisions) of this Agreement from time to
|
||||
time. No one other than the Agreement Steward has the right to modify this
|
||||
Agreement. The Eclipse Foundation is the initial Agreement Steward. The
|
||||
Eclipse Foundation may assign the responsibility to serve as the Agreement
|
||||
Steward to a suitable separate entity. Each new version of the Agreement will
|
||||
be given a distinguishing version number. The Program (including
|
||||
Contributions) may always be distributed subject to the version of the
|
||||
Agreement under which it was received. In addition, after a new version of
|
||||
the Agreement is published, Contributor may elect to distribute the Program
|
||||
(including its Contributions) under the new version. Except as expressly
|
||||
stated in Sections 2(a) and 2(b) above, Recipient receives no rights or
|
||||
licenses to the intellectual property of any Contributor under this
|
||||
Agreement, whether expressly, by implication, estoppel or otherwise. All
|
||||
rights in the Program not expressly granted under this Agreement are
|
||||
reserved.
|
||||
|
||||
This Agreement is governed by the laws of the State of New York and the
|
||||
intellectual property laws of the United States of America. No party to this
|
||||
Agreement will bring a legal action under this Agreement more than one year
|
||||
after the cause of action arose. Each party waives its rights to a jury trial
|
||||
in any resulting litigation.
|
||||
|
||||
15
examples/mysql_log/Makefile
Normal file
15
examples/mysql_log/Makefile
Normal file
@@ -0,0 +1,15 @@
|
||||
CFLAGS=-Wall -ggdb
|
||||
LDFLAGS=../../lib/libmosquitto.so.1 -lmysqlclient
|
||||
|
||||
.PHONY: all clean
|
||||
|
||||
all : mosquitto_mysql_log
|
||||
|
||||
mosquitto_mysql_log : mysql_log.o
|
||||
${CC} $^ -o $@ ${LDFLAGS}
|
||||
|
||||
mysql_log.o : mysql_log.c
|
||||
${CC} -c $^ -o $@ ${CFLAGS} -I../../lib
|
||||
|
||||
clean :
|
||||
-rm -f *.o mosquitto_mysql_log
|
||||
118
examples/mysql_log/mysql_log.c
Normal file
118
examples/mysql_log/mysql_log.c
Normal file
@@ -0,0 +1,118 @@
|
||||
#include <signal.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
|
||||
#ifndef WIN32
|
||||
# include <unistd.h>
|
||||
#else
|
||||
# include <process.h>
|
||||
# define snprintf sprintf_s
|
||||
#endif
|
||||
|
||||
#include <mosquitto.h>
|
||||
#include <mysql/mysql.h>
|
||||
|
||||
#define db_host "localhost"
|
||||
#define db_username "mqtt_log"
|
||||
#define db_password "password"
|
||||
#define db_database "mqtt_log"
|
||||
#define db_port 3306
|
||||
|
||||
#define db_query "INSERT INTO mqtt_log (topic, payload) VALUES (?,?)"
|
||||
|
||||
#define mqtt_host "localhost"
|
||||
#define mqtt_port 1883
|
||||
|
||||
static int run = 1;
|
||||
static MYSQL_STMT *stmt = NULL;
|
||||
|
||||
void handle_signal(int s)
|
||||
{
|
||||
run = 0;
|
||||
}
|
||||
|
||||
void connect_callback(struct mosquitto *mosq, void *obj, int result)
|
||||
{
|
||||
}
|
||||
|
||||
void message_callback(struct mosquitto *mosq, void *obj, const struct mosquitto_message *message)
|
||||
{
|
||||
MYSQL_BIND bind[2];
|
||||
|
||||
memset(bind, 0, sizeof(bind));
|
||||
|
||||
bind[0].buffer_type = MYSQL_TYPE_STRING;
|
||||
bind[0].buffer = message->topic;
|
||||
bind[1].buffer_type = MYSQL_TYPE_STRING;
|
||||
bind[1].buffer = message->payload;
|
||||
|
||||
mysql_stmt_bind_param(stmt, bind);
|
||||
mysql_stmt_execute(stmt);
|
||||
}
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
MYSQL *connection;
|
||||
my_bool reconnect = true;
|
||||
char clientid[24];
|
||||
struct mosquitto *mosq;
|
||||
int rc = 0;
|
||||
|
||||
signal(SIGINT, handle_signal);
|
||||
signal(SIGTERM, handle_signal);
|
||||
|
||||
mysql_library_init(0, NULL, NULL);
|
||||
mosquitto_lib_init();
|
||||
|
||||
connection = mysql_init(NULL);
|
||||
|
||||
if(connection){
|
||||
mysql_options(connection, MYSQL_OPT_RECONNECT, &reconnect);
|
||||
|
||||
connection = mysql_real_connect(connection, db_host, db_username, db_password, db_database, db_port, NULL, 0);
|
||||
|
||||
if(connection){
|
||||
stmt = mysql_stmt_init(connection);
|
||||
|
||||
mysql_stmt_prepare(stmt, db_query, strlen(db_query));
|
||||
|
||||
memset(clientid, 0, 24);
|
||||
snprintf(clientid, 23, "mysql_log_%d", getpid());
|
||||
mosq = mosquitto_new(clientid, true, connection);
|
||||
if(mosq){
|
||||
mosquitto_connect_callback_set(mosq, connect_callback);
|
||||
mosquitto_message_callback_set(mosq, message_callback);
|
||||
|
||||
|
||||
rc = mosquitto_connect(mosq, mqtt_host, mqtt_port, 60);
|
||||
|
||||
mosquitto_subscribe(mosq, NULL, "#", 0);
|
||||
|
||||
while(run){
|
||||
rc = mosquitto_loop(mosq, -1, 1);
|
||||
if(run && rc){
|
||||
sleep(20);
|
||||
mosquitto_reconnect(mosq);
|
||||
}
|
||||
}
|
||||
mosquitto_destroy(mosq);
|
||||
}
|
||||
mysql_stmt_close(stmt);
|
||||
|
||||
mysql_close(connection);
|
||||
}else{
|
||||
fprintf(stderr, "Error: Unable to connect to database.\n");
|
||||
printf("%s\n", mysql_error(connection));
|
||||
rc = 1;
|
||||
}
|
||||
}else{
|
||||
fprintf(stderr, "Error: Unable to start mysql.\n");
|
||||
rc = 1;
|
||||
}
|
||||
|
||||
mysql_library_end();
|
||||
mosquitto_lib_cleanup();
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
18
examples/temperature_conversion/Makefile
Normal file
18
examples/temperature_conversion/Makefile
Normal file
@@ -0,0 +1,18 @@
|
||||
CFLAGS=-Wall -ggdb -I../../lib -I../../lib/cpp
|
||||
LDFLAGS=-L../../lib ../../lib/cpp/libmosquittopp.so.1 ../../lib/libmosquitto.so.1
|
||||
|
||||
.PHONY: all clean
|
||||
|
||||
all : mqtt_temperature_conversion
|
||||
|
||||
mqtt_temperature_conversion : main.o temperature_conversion.o
|
||||
${CXX} $^ -o $@ ${LDFLAGS}
|
||||
|
||||
main.o : main.cpp
|
||||
${CXX} -c $^ -o $@ ${CFLAGS}
|
||||
|
||||
temperature_conversion.o : temperature_conversion.cpp
|
||||
${CXX} -c $^ -o $@ ${CFLAGS}
|
||||
|
||||
clean :
|
||||
-rm -f *.o mqtt_temperature_conversion
|
||||
23
examples/temperature_conversion/main.cpp
Normal file
23
examples/temperature_conversion/main.cpp
Normal file
@@ -0,0 +1,23 @@
|
||||
#include "temperature_conversion.h"
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
class mqtt_tempconv *tempconv;
|
||||
int rc;
|
||||
|
||||
mosqpp::lib_init();
|
||||
|
||||
tempconv = new mqtt_tempconv("tempconv", "localhost", 1883);
|
||||
|
||||
while(1){
|
||||
rc = tempconv->loop();
|
||||
if(rc){
|
||||
tempconv->reconnect();
|
||||
}
|
||||
}
|
||||
|
||||
mosqpp::lib_cleanup();
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
6
examples/temperature_conversion/readme.txt
Normal file
6
examples/temperature_conversion/readme.txt
Normal file
@@ -0,0 +1,6 @@
|
||||
This is a simple example of the C++ library mosquittopp.
|
||||
|
||||
It is a client that subscribes to the topic temperature/celsius which should
|
||||
have temperature data in text form being published to it. It reads this data as
|
||||
a Celsius temperature, converts to Farenheit and republishes on
|
||||
temperature/farenheit.
|
||||
45
examples/temperature_conversion/temperature_conversion.cpp
Normal file
45
examples/temperature_conversion/temperature_conversion.cpp
Normal file
@@ -0,0 +1,45 @@
|
||||
#include <cstdio>
|
||||
#include <cstring>
|
||||
|
||||
#include "temperature_conversion.h"
|
||||
#include <mosquittopp.h>
|
||||
|
||||
mqtt_tempconv::mqtt_tempconv(const char *id, const char *host, int port) : mosquittopp(id)
|
||||
{
|
||||
int keepalive = 60;
|
||||
|
||||
/* Connect immediately. This could also be done by calling
|
||||
* mqtt_tempconv->connect(). */
|
||||
connect(host, port, keepalive);
|
||||
};
|
||||
|
||||
void mqtt_tempconv::on_connect(int rc)
|
||||
{
|
||||
printf("Connected with code %d.\n", rc);
|
||||
if(rc == 0){
|
||||
/* Only attempt to subscribe on a successful connect. */
|
||||
subscribe(NULL, "temperature/celsius");
|
||||
}
|
||||
}
|
||||
|
||||
void mqtt_tempconv::on_message(const struct mosquitto_message *message)
|
||||
{
|
||||
double temp_celsius, temp_farenheit;
|
||||
char buf[51];
|
||||
|
||||
if(!strcmp(message->topic, "temperature/celsius")){
|
||||
memset(buf, 0, 51*sizeof(char));
|
||||
/* Copy N-1 bytes to ensure always 0 terminated. */
|
||||
memcpy(buf, message->payload, 50*sizeof(char));
|
||||
temp_celsius = atof(buf);
|
||||
temp_farenheit = temp_celsius*9.0/5.0 + 32.0;
|
||||
snprintf(buf, 50, "%f", temp_farenheit);
|
||||
publish(NULL, "temperature/farenheit", strlen(buf), buf);
|
||||
}
|
||||
}
|
||||
|
||||
void mqtt_tempconv::on_subscribe(int mid, int qos_count, const int *granted_qos)
|
||||
{
|
||||
printf("Subscription succeeded.\n");
|
||||
}
|
||||
|
||||
17
examples/temperature_conversion/temperature_conversion.h
Normal file
17
examples/temperature_conversion/temperature_conversion.h
Normal file
@@ -0,0 +1,17 @@
|
||||
#ifndef TEMPERATURE_CONVERSION_H
|
||||
#define TEMPERATURE_CONVERSION_H
|
||||
|
||||
#include <mosquittopp.h>
|
||||
|
||||
class mqtt_tempconv : public mosqpp::mosquittopp
|
||||
{
|
||||
public:
|
||||
mqtt_tempconv(const char *id, const char *host, int port);
|
||||
~mqtt_tempconv();
|
||||
|
||||
void on_connect(int rc);
|
||||
void on_message(const struct mosquitto_message *message);
|
||||
void on_subscribe(int mid, int qos_count, const int *granted_qos);
|
||||
};
|
||||
|
||||
#endif
|
||||
144
installer/mosquitto-cygwin.nsi
Normal file
144
installer/mosquitto-cygwin.nsi
Normal file
@@ -0,0 +1,144 @@
|
||||
; NSIS installer script for mosquitto
|
||||
|
||||
!include "MUI.nsh"
|
||||
|
||||
; For environment variable code
|
||||
!include "WinMessages.nsh"
|
||||
!define env_hklm 'HKLM "SYSTEM\CurrentControlSet\Control\Session Manager\Environment"'
|
||||
|
||||
Name "mosquitto"
|
||||
!define VERSION 1.3.1
|
||||
OutFile "mosquitto-${VERSION}-install-cygwin.exe"
|
||||
|
||||
InstallDir "$PROGRAMFILES\mosquitto"
|
||||
|
||||
;--------------------------------
|
||||
; Installer pages
|
||||
!insertmacro MUI_PAGE_WELCOME
|
||||
!insertmacro MUI_PAGE_COMPONENTS
|
||||
!insertmacro MUI_PAGE_DIRECTORY
|
||||
!insertmacro MUI_PAGE_INSTFILES
|
||||
!insertmacro MUI_PAGE_FINISH
|
||||
|
||||
|
||||
;--------------------------------
|
||||
; Uninstaller pages
|
||||
!insertmacro MUI_UNPAGE_WELCOME
|
||||
!insertmacro MUI_UNPAGE_CONFIRM
|
||||
!insertmacro MUI_UNPAGE_INSTFILES
|
||||
!insertmacro MUI_UNPAGE_FINISH
|
||||
|
||||
;--------------------------------
|
||||
; Languages
|
||||
|
||||
!insertmacro MUI_LANGUAGE "English"
|
||||
|
||||
;--------------------------------
|
||||
; Installer sections
|
||||
|
||||
Section "Files" SecInstall
|
||||
SectionIn RO
|
||||
SetOutPath "$INSTDIR"
|
||||
File "c:\cygwin\bin\cygwin1.dll"
|
||||
File "c:\cygwin\bin\cyggcc_s-1.dll"
|
||||
File "c:\cygwin\bin\cygcrypto-1.0.0.dll"
|
||||
File "c:\cygwin\bin\cygssl-1.0.0.dll"
|
||||
File "c:\cygwin\bin\cygz.dll"
|
||||
File "..\src\mosquitto.exe"
|
||||
File "..\build\src\Release\mosquitto_passwd.exe"
|
||||
File "..\build\client\Release\mosquitto_pub.exe"
|
||||
File "..\build\client\Release\mosquitto_sub.exe"
|
||||
File "..\build\lib\Release\mosquitto.dll"
|
||||
File "..\build\lib\cpp\Release\mosquittopp.dll"
|
||||
File "..\aclfile.example"
|
||||
File "..\ChangeLog.txt"
|
||||
File "..\mosquitto.conf"
|
||||
File "..\pwfile.example"
|
||||
File "..\readme.txt"
|
||||
File "..\readme-windows.txt"
|
||||
File "C:\pthreads\Pre-built.2\dll\x86\pthreadVC2.dll"
|
||||
File "C:\OpenSSL-Win32\libeay32.dll"
|
||||
File "C:\OpenSSL-Win32\ssleay32.dll"
|
||||
File "..\LICENSE.txt"
|
||||
File "..\LICENSE-3rd-party.txt"
|
||||
|
||||
SetOutPath "$INSTDIR\devel"
|
||||
File "..\lib\mosquitto.h"
|
||||
File "..\build\lib\Release\mosquitto.lib"
|
||||
File "..\lib\cpp\mosquittopp.h"
|
||||
File "..\build\lib\cpp\Release\mosquittopp.lib"
|
||||
File "..\src\mosquitto_plugin.h"
|
||||
|
||||
SetOutPath "$INSTDIR\python"
|
||||
File "..\lib\python\mosquitto.py"
|
||||
File "..\lib\python\setup.py"
|
||||
File "..\lib\python\sub.py"
|
||||
|
||||
WriteUninstaller "$INSTDIR\Uninstall.exe"
|
||||
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Mosquitto" "DisplayName" "Mosquitto MQTT broker"
|
||||
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Mosquitto" "UninstallString" "$\"$INSTDIR\Uninstall.exe$\""
|
||||
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Mosquitto" "QuietUninstallString" "$\"$INSTDIR\Uninstall.exe$\" /S"
|
||||
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Mosquitto" "HelpLink" "http://mosquitto.org/"
|
||||
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Mosquitto" "URLInfoAbout" "http://mosquitto.org/"
|
||||
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Mosquitto" "DisplayVersion" "${VERSION}"
|
||||
WriteRegDWORD HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Mosquitto" "NoModify" "1"
|
||||
WriteRegDWORD HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Mosquitto" "NoRepair" "1"
|
||||
|
||||
WriteRegExpandStr ${env_hklm} MOSQUITTO_DIR $INSTDIR
|
||||
SendMessage ${HWND_BROADCAST} ${WM_WININICHANGE} 0 "STR:Environment" /TIMEOUT=5000
|
||||
SectionEnd
|
||||
|
||||
Section "Service" SecService
|
||||
ExecWait '"$INSTDIR\mosquitto.exe" install'
|
||||
SectionEnd
|
||||
|
||||
Section "Uninstall"
|
||||
ExecWait '"$INSTDIR\mosquitto.exe" uninstall'
|
||||
Delete "$INSTDIR\cygwin1.dll"
|
||||
Delete "$INSTDIR\cyggcc_s-1.dll"
|
||||
Delete "$INSTDIR\cygcrypto-1.0.0.dll"
|
||||
Delete "$INSTDIR\cygssl-1.0.0.dll"
|
||||
Delete "$INSTDIR\cygz.dll"
|
||||
Delete "$INSTDIR\mosquitto.exe"
|
||||
Delete "$INSTDIR\mosquitto_passwd.exe"
|
||||
Delete "$INSTDIR\mosquitto_pub.exe"
|
||||
Delete "$INSTDIR\mosquitto_sub.exe"
|
||||
Delete "$INSTDIR\mosquitto.dll"
|
||||
Delete "$INSTDIR\mosquittopp.dll"
|
||||
Delete "$INSTDIR\aclfile.example"
|
||||
Delete "$INSTDIR\ChangeLog.txt"
|
||||
Delete "$INSTDIR\mosquitto.conf"
|
||||
Delete "$INSTDIR\pwfile.example"
|
||||
Delete "$INSTDIR\readme.txt"
|
||||
Delete "$INSTDIR\readme-windows.txt"
|
||||
Delete "$INSTDIR\pthreadVC2.dll"
|
||||
Delete "$INSTDIR\libeay32.dll"
|
||||
Delete "$INSTDIR\ssleay32.dll"
|
||||
Delete "$INSTDIR\LICENSE.txt"
|
||||
Delete "$INSTDIR\LICENSE-3rd-party.txt"
|
||||
|
||||
Delete "$INSTDIR\devel\mosquitto.h"
|
||||
Delete "$INSTDIR\devel\mosquitto.lib"
|
||||
Delete "$INSTDIR\devel\mosquittopp.h"
|
||||
Delete "$INSTDIR\devel\mosquittopp.lib"
|
||||
Delete "$INSTDIR\devel\mosquitto_plugin.h"
|
||||
|
||||
Delete "$INSTDIR\python\mosquitto.py"
|
||||
Delete "$INSTDIR\python\setup.py"
|
||||
Delete "$INSTDIR\python\sub.py"
|
||||
|
||||
Delete "$INSTDIR\Uninstall.exe"
|
||||
RMDir "$INSTDIR"
|
||||
DeleteRegKey HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Mosquitto"
|
||||
|
||||
DeleteRegValue ${env_hklm} MOSQUITTO_DIR
|
||||
SendMessage ${HWND_BROADCAST} ${WM_WININICHANGE} 0 "STR:Environment" /TIMEOUT=5000
|
||||
SectionEnd
|
||||
|
||||
LangString DESC_SecInstall ${LANG_ENGLISH} "The main installation."
|
||||
LangString DESC_SecService ${LANG_ENGLISH} "Install mosquitto as a Windows service?"
|
||||
!insertmacro MUI_FUNCTION_DESCRIPTION_BEGIN
|
||||
!insertmacro MUI_DESCRIPTION_TEXT ${SecInstall} $(DESC_SecInstall)
|
||||
!insertmacro MUI_DESCRIPTION_TEXT ${SecService} $(DESC_SecService)
|
||||
!insertmacro MUI_FUNCTION_DESCRIPTION_END
|
||||
|
||||
134
installer/mosquitto.nsi
Normal file
134
installer/mosquitto.nsi
Normal file
@@ -0,0 +1,134 @@
|
||||
; NSIS installer script for mosquitto
|
||||
|
||||
!include "MUI.nsh"
|
||||
|
||||
; For environment variable code
|
||||
!include "WinMessages.nsh"
|
||||
!define env_hklm 'HKLM "SYSTEM\CurrentControlSet\Control\Session Manager\Environment"'
|
||||
|
||||
Name "mosquitto"
|
||||
!define VERSION 1.3.1
|
||||
OutFile "mosquitto-${VERSION}-install-win32.exe"
|
||||
|
||||
InstallDir "$PROGRAMFILES\mosquitto"
|
||||
|
||||
;--------------------------------
|
||||
; Installer pages
|
||||
!insertmacro MUI_PAGE_WELCOME
|
||||
!insertmacro MUI_PAGE_COMPONENTS
|
||||
!insertmacro MUI_PAGE_DIRECTORY
|
||||
!insertmacro MUI_PAGE_INSTFILES
|
||||
!insertmacro MUI_PAGE_FINISH
|
||||
|
||||
|
||||
;--------------------------------
|
||||
; Uninstaller pages
|
||||
!insertmacro MUI_UNPAGE_WELCOME
|
||||
!insertmacro MUI_UNPAGE_CONFIRM
|
||||
!insertmacro MUI_UNPAGE_INSTFILES
|
||||
!insertmacro MUI_UNPAGE_FINISH
|
||||
|
||||
;--------------------------------
|
||||
; Languages
|
||||
|
||||
!insertmacro MUI_LANGUAGE "English"
|
||||
|
||||
;--------------------------------
|
||||
; Installer sections
|
||||
|
||||
Section "Files" SecInstall
|
||||
SectionIn RO
|
||||
SetOutPath "$INSTDIR"
|
||||
File "..\build\src\Release\mosquitto.exe"
|
||||
File "..\build\src\Release\mosquitto_passwd.exe"
|
||||
File "..\build\client\Release\mosquitto_pub.exe"
|
||||
File "..\build\client\Release\mosquitto_sub.exe"
|
||||
File "..\build\lib\Release\mosquitto.dll"
|
||||
File "..\build\lib\cpp\Release\mosquittopp.dll"
|
||||
File "..\aclfile.example"
|
||||
File "..\ChangeLog.txt"
|
||||
File "..\mosquitto.conf"
|
||||
File "..\pwfile.example"
|
||||
File "..\readme.txt"
|
||||
File "..\readme-windows.txt"
|
||||
File "C:\pthreads\Pre-built.2\dll\x86\pthreadVC2.dll"
|
||||
File "C:\OpenSSL-Win32\libeay32.dll"
|
||||
File "C:\OpenSSL-Win32\ssleay32.dll"
|
||||
File "..\LICENSE.txt"
|
||||
File "..\LICENSE-3rd-party.txt"
|
||||
|
||||
SetOutPath "$INSTDIR\devel"
|
||||
File "..\lib\mosquitto.h"
|
||||
File "..\build\lib\Release\mosquitto.lib"
|
||||
File "..\lib\cpp\mosquittopp.h"
|
||||
File "..\build\lib\cpp\Release\mosquittopp.lib"
|
||||
File "..\src\mosquitto_plugin.h"
|
||||
|
||||
SetOutPath "$INSTDIR\python"
|
||||
File "..\lib\python\mosquitto.py"
|
||||
File "..\lib\python\setup.py"
|
||||
File "..\lib\python\sub.py"
|
||||
|
||||
WriteUninstaller "$INSTDIR\Uninstall.exe"
|
||||
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Mosquitto" "DisplayName" "Mosquitto MQTT broker"
|
||||
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Mosquitto" "UninstallString" "$\"$INSTDIR\Uninstall.exe$\""
|
||||
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Mosquitto" "QuietUninstallString" "$\"$INSTDIR\Uninstall.exe$\" /S"
|
||||
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Mosquitto" "HelpLink" "http://mosquitto.org/"
|
||||
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Mosquitto" "URLInfoAbout" "http://mosquitto.org/"
|
||||
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Mosquitto" "DisplayVersion" "${VERSION}"
|
||||
WriteRegDWORD HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Mosquitto" "NoModify" "1"
|
||||
WriteRegDWORD HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Mosquitto" "NoRepair" "1"
|
||||
|
||||
WriteRegExpandStr ${env_hklm} MOSQUITTO_DIR $INSTDIR
|
||||
SendMessage ${HWND_BROADCAST} ${WM_WININICHANGE} 0 "STR:Environment" /TIMEOUT=5000
|
||||
SectionEnd
|
||||
|
||||
Section "Service" SecService
|
||||
ExecWait '"$INSTDIR\mosquitto.exe" install'
|
||||
SectionEnd
|
||||
|
||||
Section "Uninstall"
|
||||
ExecWait '"$INSTDIR\mosquitto.exe" uninstall'
|
||||
Delete "$INSTDIR\mosquitto.exe"
|
||||
Delete "$INSTDIR\mosquitto_passwd.exe"
|
||||
Delete "$INSTDIR\mosquitto_pub.exe"
|
||||
Delete "$INSTDIR\mosquitto_sub.exe"
|
||||
Delete "$INSTDIR\mosquitto.dll"
|
||||
Delete "$INSTDIR\mosquittopp.dll"
|
||||
Delete "$INSTDIR\aclfile.example"
|
||||
Delete "$INSTDIR\ChangeLog.txt"
|
||||
Delete "$INSTDIR\mosquitto.conf"
|
||||
Delete "$INSTDIR\pwfile.example"
|
||||
Delete "$INSTDIR\readme.txt"
|
||||
Delete "$INSTDIR\readme-windows.txt"
|
||||
Delete "$INSTDIR\pthreadVC2.dll"
|
||||
Delete "$INSTDIR\libeay32.dll"
|
||||
Delete "$INSTDIR\ssleay32.dll"
|
||||
Delete "$INSTDIR\LICENSE.txt"
|
||||
Delete "$INSTDIR\LICENSE-3rd-party.txt"
|
||||
|
||||
Delete "$INSTDIR\devel\mosquitto.h"
|
||||
Delete "$INSTDIR\devel\mosquitto.lib"
|
||||
Delete "$INSTDIR\devel\mosquittopp.h"
|
||||
Delete "$INSTDIR\devel\mosquittopp.lib"
|
||||
Delete "$INSTDIR\devel\mosquitto_plugin.h"
|
||||
|
||||
Delete "$INSTDIR\python\mosquitto.py"
|
||||
Delete "$INSTDIR\python\setup.py"
|
||||
Delete "$INSTDIR\python\sub.py"
|
||||
|
||||
Delete "$INSTDIR\Uninstall.exe"
|
||||
RMDir "$INSTDIR"
|
||||
DeleteRegKey HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Mosquitto"
|
||||
|
||||
DeleteRegValue ${env_hklm} MOSQUITTO_DIR
|
||||
SendMessage ${HWND_BROADCAST} ${WM_WININICHANGE} 0 "STR:Environment" /TIMEOUT=5000
|
||||
SectionEnd
|
||||
|
||||
LangString DESC_SecInstall ${LANG_ENGLISH} "The main installation."
|
||||
LangString DESC_SecService ${LANG_ENGLISH} "Install mosquitto as a Windows service?"
|
||||
!insertmacro MUI_FUNCTION_DESCRIPTION_BEGIN
|
||||
!insertmacro MUI_DESCRIPTION_TEXT ${SecInstall} $(DESC_SecInstall)
|
||||
!insertmacro MUI_DESCRIPTION_TEXT ${SecService} $(DESC_SecService)
|
||||
!insertmacro MUI_FUNCTION_DESCRIPTION_END
|
||||
|
||||
71
lib/CMakeLists.txt
Normal file
71
lib/CMakeLists.txt
Normal file
@@ -0,0 +1,71 @@
|
||||
add_subdirectory(cpp)
|
||||
|
||||
option(WITH_THREADING "Include client library threading support?" ON)
|
||||
if (${WITH_THREADING} STREQUAL ON)
|
||||
add_definitions("-DWITH_THREADING")
|
||||
if (WIN32)
|
||||
set (PTHREAD_LIBRARIES C:\\pthreads\\Pre-built.2\\lib\\x86\\pthreadVC2.lib)
|
||||
set (PTHREAD_INCLUDE_DIR C:\\pthreads\\Pre-built.2\\include)
|
||||
else (WIN32)
|
||||
set (PTHREAD_LIBRARIES pthread)
|
||||
set (PTHREAD_INCLUDE_DIR "")
|
||||
endif (WIN32)
|
||||
else (${WITH_THREADING} STREQUAL ON)
|
||||
set (PTHREAD_LIBRARIES "")
|
||||
set (PTHREAD_INCLUDE_DIR "")
|
||||
endif (${WITH_THREADING} STREQUAL ON)
|
||||
|
||||
include_directories(${mosquitto_SOURCE_DIR} ${mosquitto_SOURCE_DIR}/lib
|
||||
${STDBOOL_H_PATH} ${STDINT_H_PATH}
|
||||
${OPENSSL_INCLUDE_DIR} ${PTHREAD_INCLUDE_DIR})
|
||||
link_directories(${mosquitto_SOURCE_DIR}/lib)
|
||||
|
||||
add_library(libmosquitto SHARED
|
||||
logging_mosq.c logging_mosq.h
|
||||
memory_mosq.c memory_mosq.h
|
||||
messages_mosq.c messages_mosq.h
|
||||
mosquitto.c mosquitto.h
|
||||
mosquitto_internal.h
|
||||
mqtt3_protocol.h
|
||||
net_mosq.c net_mosq.h
|
||||
read_handle.c read_handle.h
|
||||
read_handle_client.c
|
||||
read_handle_shared.c
|
||||
send_client_mosq.c
|
||||
send_mosq.c send_mosq.h
|
||||
srv_mosq.c
|
||||
thread_mosq.c
|
||||
time_mosq.c
|
||||
tls_mosq.c
|
||||
util_mosq.c util_mosq.h
|
||||
will_mosq.c will_mosq.h)
|
||||
|
||||
set (LIBRARIES ${OPENSSL_LIBRARIES} ${PTHREAD_LIBRARIES})
|
||||
|
||||
if (UNIX AND NOT APPLE)
|
||||
set (LIBRARIES ${LIBRARIES} rt)
|
||||
endif (UNIX AND NOT APPLE)
|
||||
|
||||
if (WIN32)
|
||||
set (LIBRARIES ${LIBRARIES} ws2_32)
|
||||
endif (WIN32)
|
||||
|
||||
option(WITH_SRV "Include SRV lookup support?" ON)
|
||||
if (${WITH_SRV} STREQUAL ON)
|
||||
set (LIBRARIES ${LIBRARIES} cares)
|
||||
endif (${WITH_SRV} STREQUAL ON)
|
||||
|
||||
target_link_libraries(libmosquitto ${LIBRARIES})
|
||||
|
||||
set_target_properties(libmosquitto PROPERTIES
|
||||
OUTPUT_NAME mosquitto
|
||||
VERSION ${VERSION}
|
||||
SOVERSION 1
|
||||
)
|
||||
|
||||
install(TARGETS libmosquitto RUNTIME DESTINATION ${BINDIR} LIBRARY DESTINATION ${LIBDIR})
|
||||
install(FILES mosquitto.h DESTINATION ${INCLUDEDIR})
|
||||
|
||||
if (UNIX)
|
||||
install(CODE "EXEC_PROGRAM(/sbin/ldconfig)")
|
||||
endif (UNIX)
|
||||
96
lib/Makefile
Normal file
96
lib/Makefile
Normal file
@@ -0,0 +1,96 @@
|
||||
include ../config.mk
|
||||
|
||||
.PHONY : really clean install
|
||||
|
||||
MOSQ_OBJS=mosquitto.o \
|
||||
logging_mosq.o \
|
||||
memory_mosq.o \
|
||||
messages_mosq.o \
|
||||
net_mosq.o \
|
||||
read_handle.o \
|
||||
read_handle_client.o \
|
||||
read_handle_shared.o \
|
||||
send_mosq.o \
|
||||
send_client_mosq.o \
|
||||
srv_mosq.o \
|
||||
thread_mosq.o \
|
||||
time_mosq.o \
|
||||
tls_mosq.o \
|
||||
util_mosq.o \
|
||||
will_mosq.o
|
||||
|
||||
all : libmosquitto.so.${SOVERSION} libmosquitto.a
|
||||
$(MAKE) -C cpp
|
||||
|
||||
install : all
|
||||
$(INSTALL) -d ${DESTDIR}$(prefix)/lib${LIB_SUFFIX}/
|
||||
$(INSTALL) -s libmosquitto.so.${SOVERSION} ${DESTDIR}${prefix}/lib${LIB_SUFFIX}/libmosquitto.so.${SOVERSION}
|
||||
ln -sf libmosquitto.so.${SOVERSION} ${DESTDIR}${prefix}/lib${LIB_SUFFIX}/libmosquitto.so
|
||||
$(INSTALL) -d ${DESTDIR}${prefix}/include/
|
||||
$(INSTALL) mosquitto.h ${DESTDIR}${prefix}/include/mosquitto.h
|
||||
$(MAKE) -C cpp install
|
||||
|
||||
uninstall :
|
||||
-rm -f ${DESTDIR}${prefix}/lib${LIB_SUFFIX}/libmosquitto.so.${SOVERSION}
|
||||
-rm -f ${DESTDIR}${prefix}/lib${LIB_SUFFIX}/libmosquitto.so
|
||||
-rm -f ${DESTDIR}${prefix}/include/mosquitto.h
|
||||
|
||||
reallyclean : clean
|
||||
|
||||
clean :
|
||||
-rm -f *.o libmosquitto.so.${SOVERSION} libmosquitto.so libmosquitto.a
|
||||
$(MAKE) -C cpp clean
|
||||
|
||||
libmosquitto.so.${SOVERSION} : ${MOSQ_OBJS}
|
||||
$(CC) -shared $(LIB_LDFLAGS) $^ -o $@ ${LIB_LIBS}
|
||||
|
||||
libmosquitto.a : ${MOSQ_OBJS}
|
||||
$(AR) cr $@ $^
|
||||
mosquitto.o : mosquitto.c mosquitto.h
|
||||
$(CC) $(LIB_CFLAGS) -c $< -o $@
|
||||
|
||||
logging_mosq.o : logging_mosq.c logging_mosq.h
|
||||
$(CC) $(LIB_CFLAGS) -c $< -o $@
|
||||
|
||||
messages_mosq.o : messages_mosq.c messages_mosq.h
|
||||
$(CC) $(LIB_CFLAGS) -c $< -o $@
|
||||
|
||||
memory_mosq.o : memory_mosq.c memory_mosq.h
|
||||
$(CC) $(LIB_CFLAGS) -c $< -o $@
|
||||
|
||||
net_mosq.o : net_mosq.c net_mosq.h
|
||||
$(CC) $(LIB_CFLAGS) -c $< -o $@
|
||||
|
||||
read_handle.o : read_handle.c read_handle.h
|
||||
$(CC) $(LIB_CFLAGS) -c $< -o $@
|
||||
|
||||
read_handle_client.o : read_handle_client.c read_handle.h
|
||||
$(CC) $(LIB_CFLAGS) -c $< -o $@
|
||||
|
||||
read_handle_shared.o : read_handle_shared.c read_handle.h
|
||||
$(CC) $(LIB_CFLAGS) -c $< -o $@
|
||||
|
||||
send_mosq.o : send_mosq.c send_mosq.h
|
||||
$(CC) $(LIB_CFLAGS) -c $< -o $@
|
||||
|
||||
send_client_mosq.o : send_client_mosq.c send_mosq.h
|
||||
$(CC) $(LIB_CFLAGS) -c $< -o $@
|
||||
|
||||
srv_mosq.o : srv_mosq.c
|
||||
$(CC) $(LIB_CFLAGS) -c $< -o $@
|
||||
|
||||
thread_mosq.o : thread_mosq.c
|
||||
$(CC) $(LIB_CFLAGS) -c $< -o $@
|
||||
|
||||
time_mosq.o : time_mosq.c
|
||||
$(CC) $(LIB_CFLAGS) -c $< -o $@
|
||||
|
||||
tls_mosq.o : tls_mosq.c
|
||||
$(CC) $(LIB_CFLAGS) -c $< -o $@
|
||||
|
||||
util_mosq.o : util_mosq.c util_mosq.h
|
||||
$(CC) $(LIB_CFLAGS) -c $< -o $@
|
||||
|
||||
will_mosq.o : will_mosq.c will_mosq.h
|
||||
$(CC) $(LIB_CFLAGS) -c $< -o $@
|
||||
|
||||
18
lib/cpp/CMakeLists.txt
Normal file
18
lib/cpp/CMakeLists.txt
Normal file
@@ -0,0 +1,18 @@
|
||||
include_directories(${mosquitto_SOURCE_DIR}/lib ${mosquitto_SOURCE_DIR}/lib/cpp
|
||||
${STDBOOL_H_PATH} ${STDINT_H_PATH})
|
||||
link_directories(${mosquitto_BINARY_DIR}/lib)
|
||||
|
||||
add_library(mosquittopp SHARED
|
||||
mosquittopp.cpp mosquittopp.h)
|
||||
|
||||
target_link_libraries(mosquittopp mosquitto)
|
||||
set_target_properties(mosquittopp PROPERTIES
|
||||
VERSION ${VERSION}
|
||||
SOVERSION 1
|
||||
)
|
||||
install(TARGETS mosquittopp RUNTIME DESTINATION ${BINDIR} LIBRARY DESTINATION ${LIBDIR})
|
||||
install(FILES mosquittopp.h DESTINATION ${INCLUDEDIR})
|
||||
|
||||
if (UNIX)
|
||||
install(CODE "EXEC_PROGRAM(/sbin/ldconfig)")
|
||||
endif (UNIX)
|
||||
31
lib/cpp/Makefile
Normal file
31
lib/cpp/Makefile
Normal file
@@ -0,0 +1,31 @@
|
||||
include ../../config.mk
|
||||
|
||||
ifneq ($(UNAME),SunOS)
|
||||
LIB_LDFLAGS:=$(LDFLAGS) -Wl,-soname,libmosquittopp.so.${SOVERSION}
|
||||
endif
|
||||
|
||||
.PHONY : clean install
|
||||
|
||||
all : libmosquittopp.so.${SOVERSION}
|
||||
|
||||
install : all
|
||||
$(INSTALL) -d ${DESTDIR}$(prefix)/lib${LIB_SUFFIX}/
|
||||
$(INSTALL) -s libmosquittopp.so.${SOVERSION} ${DESTDIR}${prefix}/lib${LIB_SUFFIX}/libmosquittopp.so.${SOVERSION}
|
||||
ln -sf libmosquittopp.so.${SOVERSION} ${DESTDIR}${prefix}/lib${LIB_SUFFIX}/libmosquittopp.so
|
||||
$(INSTALL) -d ${DESTDIR}${prefix}/include/
|
||||
$(INSTALL) mosquittopp.h ${DESTDIR}${prefix}/include/mosquittopp.h
|
||||
|
||||
uninstall :
|
||||
-rm -f ${DESTDIR}${prefix}/lib${LIB_SUFFIX}/libmosquittopp.so.${SOVERSION}
|
||||
-rm -f ${DESTDIR}${prefix}/lib${LIB_SUFFIX}/libmosquittopp.so
|
||||
-rm -f ${DESTDIR}${prefix}/include/mosquittopp.h
|
||||
|
||||
clean :
|
||||
-rm -f *.o libmosquittopp.so.${SOVERSION}
|
||||
|
||||
libmosquittopp.so.${SOVERSION} : mosquittopp.o
|
||||
$(CXX) -shared $(LIB_LDFLAGS) $< -o $@ ../libmosquitto.so.${SOVERSION}
|
||||
|
||||
mosquittopp.o : mosquittopp.cpp mosquittopp.h
|
||||
$(CXX) $(LIB_CXXFLAGS) -c $< -o $@
|
||||
|
||||
292
lib/cpp/mosquittopp.cpp
Normal file
292
lib/cpp/mosquittopp.cpp
Normal file
@@ -0,0 +1,292 @@
|
||||
/*
|
||||
Copyright (c) 2010-2014 Roger Light <roger@atchoo.org>
|
||||
|
||||
All rights reserved. This program and the accompanying materials
|
||||
are made available under the terms of the Eclipse Public License v1.0
|
||||
and Eclipse Distribution License v1.0 which accompany this distribution.
|
||||
|
||||
The Eclipse Public License is available at
|
||||
http://www.eclipse.org/legal/epl-v10.html
|
||||
and the Eclipse Distribution License is available at
|
||||
http://www.eclipse.org/org/documents/edl-v10.php.
|
||||
|
||||
Contributors:
|
||||
Roger Light - initial implementation and documentation.
|
||||
*/
|
||||
|
||||
#include <cstdlib>
|
||||
#include <mosquitto.h>
|
||||
#include <mosquittopp.h>
|
||||
|
||||
namespace mosqpp {
|
||||
|
||||
static void on_connect_wrapper(struct mosquitto *mosq, void *userdata, int rc)
|
||||
{
|
||||
class mosquittopp *m = (class mosquittopp *)userdata;
|
||||
m->on_connect(rc);
|
||||
}
|
||||
|
||||
static void on_disconnect_wrapper(struct mosquitto *mosq, void *userdata, int rc)
|
||||
{
|
||||
class mosquittopp *m = (class mosquittopp *)userdata;
|
||||
m->on_disconnect(rc);
|
||||
}
|
||||
|
||||
static void on_publish_wrapper(struct mosquitto *mosq, void *userdata, int mid)
|
||||
{
|
||||
class mosquittopp *m = (class mosquittopp *)userdata;
|
||||
m->on_publish(mid);
|
||||
}
|
||||
|
||||
static void on_message_wrapper(struct mosquitto *mosq, void *userdata, const struct mosquitto_message *message)
|
||||
{
|
||||
class mosquittopp *m = (class mosquittopp *)userdata;
|
||||
m->on_message(message);
|
||||
}
|
||||
|
||||
static void on_subscribe_wrapper(struct mosquitto *mosq, void *userdata, int mid, int qos_count, const int *granted_qos)
|
||||
{
|
||||
class mosquittopp *m = (class mosquittopp *)userdata;
|
||||
m->on_subscribe(mid, qos_count, granted_qos);
|
||||
}
|
||||
|
||||
static void on_unsubscribe_wrapper(struct mosquitto *mosq, void *userdata, int mid)
|
||||
{
|
||||
class mosquittopp *m = (class mosquittopp *)userdata;
|
||||
m->on_unsubscribe(mid);
|
||||
}
|
||||
|
||||
|
||||
static void on_log_wrapper(struct mosquitto *mosq, void *userdata, int level, const char *str)
|
||||
{
|
||||
class mosquittopp *m = (class mosquittopp *)userdata;
|
||||
m->on_log(level, str);
|
||||
}
|
||||
|
||||
int lib_version(int *major, int *minor, int *revision)
|
||||
{
|
||||
if(major) *major = LIBMOSQUITTO_MAJOR;
|
||||
if(minor) *minor = LIBMOSQUITTO_MINOR;
|
||||
if(revision) *revision = LIBMOSQUITTO_REVISION;
|
||||
return LIBMOSQUITTO_VERSION_NUMBER;
|
||||
}
|
||||
|
||||
int lib_init()
|
||||
{
|
||||
return mosquitto_lib_init();
|
||||
}
|
||||
|
||||
int lib_cleanup()
|
||||
{
|
||||
return mosquitto_lib_cleanup();
|
||||
}
|
||||
|
||||
const char* strerror(int mosq_errno)
|
||||
{
|
||||
return mosquitto_strerror(mosq_errno);
|
||||
}
|
||||
|
||||
const char* connack_string(int connack_code)
|
||||
{
|
||||
return mosquitto_connack_string(connack_code);
|
||||
}
|
||||
|
||||
int sub_topic_tokenise(const char *subtopic, char ***topics, int *count)
|
||||
{
|
||||
return mosquitto_sub_topic_tokenise(subtopic, topics, count);
|
||||
}
|
||||
|
||||
int sub_topic_tokens_free(char ***topics, int count)
|
||||
{
|
||||
return mosquitto_sub_topic_tokens_free(topics, count);
|
||||
}
|
||||
|
||||
int topic_matches_sub(const char *sub, const char *topic, bool *result)
|
||||
{
|
||||
return mosquitto_topic_matches_sub(sub, topic, result);
|
||||
}
|
||||
|
||||
mosquittopp::mosquittopp(const char *id, bool clean_session)
|
||||
{
|
||||
m_mosq = mosquitto_new(id, clean_session, this);
|
||||
mosquitto_connect_callback_set(m_mosq, on_connect_wrapper);
|
||||
mosquitto_disconnect_callback_set(m_mosq, on_disconnect_wrapper);
|
||||
mosquitto_publish_callback_set(m_mosq, on_publish_wrapper);
|
||||
mosquitto_message_callback_set(m_mosq, on_message_wrapper);
|
||||
mosquitto_subscribe_callback_set(m_mosq, on_subscribe_wrapper);
|
||||
mosquitto_unsubscribe_callback_set(m_mosq, on_unsubscribe_wrapper);
|
||||
mosquitto_log_callback_set(m_mosq, on_log_wrapper);
|
||||
}
|
||||
|
||||
mosquittopp::~mosquittopp()
|
||||
{
|
||||
mosquitto_destroy(m_mosq);
|
||||
}
|
||||
|
||||
int mosquittopp::reinitialise(const char *id, bool clean_session)
|
||||
{
|
||||
int rc;
|
||||
rc = mosquitto_reinitialise(m_mosq, id, clean_session, this);
|
||||
if(rc == MOSQ_ERR_SUCCESS){
|
||||
mosquitto_connect_callback_set(m_mosq, on_connect_wrapper);
|
||||
mosquitto_disconnect_callback_set(m_mosq, on_disconnect_wrapper);
|
||||
mosquitto_publish_callback_set(m_mosq, on_publish_wrapper);
|
||||
mosquitto_message_callback_set(m_mosq, on_message_wrapper);
|
||||
mosquitto_subscribe_callback_set(m_mosq, on_subscribe_wrapper);
|
||||
mosquitto_unsubscribe_callback_set(m_mosq, on_unsubscribe_wrapper);
|
||||
mosquitto_log_callback_set(m_mosq, on_log_wrapper);
|
||||
}
|
||||
return rc;
|
||||
}
|
||||
|
||||
int mosquittopp::connect(const char *host, int port, int keepalive)
|
||||
{
|
||||
return mosquitto_connect(m_mosq, host, port, keepalive);
|
||||
}
|
||||
|
||||
int mosquittopp::connect(const char *host, int port, int keepalive, const char *bind_address)
|
||||
{
|
||||
return mosquitto_connect_bind(m_mosq, host, port, keepalive, bind_address);
|
||||
}
|
||||
|
||||
int mosquittopp::connect_async(const char *host, int port, int keepalive)
|
||||
{
|
||||
return mosquitto_connect_async(m_mosq, host, port, keepalive);
|
||||
}
|
||||
|
||||
int mosquittopp::connect_async(const char *host, int port, int keepalive, const char *bind_address)
|
||||
{
|
||||
return mosquitto_connect_bind_async(m_mosq, host, port, keepalive, bind_address);
|
||||
}
|
||||
|
||||
int mosquittopp::reconnect()
|
||||
{
|
||||
return mosquitto_reconnect(m_mosq);
|
||||
}
|
||||
|
||||
int mosquittopp::reconnect_async()
|
||||
{
|
||||
return mosquitto_reconnect_async(m_mosq);
|
||||
}
|
||||
|
||||
int mosquittopp::disconnect()
|
||||
{
|
||||
return mosquitto_disconnect(m_mosq);
|
||||
}
|
||||
|
||||
int mosquittopp::socket()
|
||||
{
|
||||
return mosquitto_socket(m_mosq);
|
||||
}
|
||||
|
||||
int mosquittopp::will_set(const char *topic, int payloadlen, const void *payload, int qos, bool retain)
|
||||
{
|
||||
return mosquitto_will_set(m_mosq, topic, payloadlen, payload, qos, retain);
|
||||
}
|
||||
|
||||
int mosquittopp::will_clear()
|
||||
{
|
||||
return mosquitto_will_clear(m_mosq);
|
||||
}
|
||||
|
||||
int mosquittopp::username_pw_set(const char *username, const char *password)
|
||||
{
|
||||
return mosquitto_username_pw_set(m_mosq, username, password);
|
||||
}
|
||||
|
||||
int mosquittopp::publish(int *mid, const char *topic, int payloadlen, const void *payload, int qos, bool retain)
|
||||
{
|
||||
return mosquitto_publish(m_mosq, mid, topic, payloadlen, payload, qos, retain);
|
||||
}
|
||||
|
||||
void mosquittopp::reconnect_delay_set(unsigned int reconnect_delay, unsigned int reconnect_delay_max, bool reconnect_exponential_backoff)
|
||||
{
|
||||
mosquitto_reconnect_delay_set(m_mosq, reconnect_delay, reconnect_delay_max, reconnect_exponential_backoff);
|
||||
}
|
||||
|
||||
int mosquittopp::max_inflight_messages_set(unsigned int max_inflight_messages)
|
||||
{
|
||||
return mosquitto_max_inflight_messages_set(m_mosq, max_inflight_messages);
|
||||
}
|
||||
|
||||
void mosquittopp::message_retry_set(unsigned int message_retry)
|
||||
{
|
||||
mosquitto_message_retry_set(m_mosq, message_retry);
|
||||
}
|
||||
|
||||
int mosquittopp::subscribe(int *mid, const char *sub, int qos)
|
||||
{
|
||||
return mosquitto_subscribe(m_mosq, mid, sub, qos);
|
||||
}
|
||||
|
||||
int mosquittopp::unsubscribe(int *mid, const char *sub)
|
||||
{
|
||||
return mosquitto_unsubscribe(m_mosq, mid, sub);
|
||||
}
|
||||
|
||||
int mosquittopp::loop(int timeout, int max_packets)
|
||||
{
|
||||
return mosquitto_loop(m_mosq, timeout, max_packets);
|
||||
}
|
||||
|
||||
int mosquittopp::loop_misc()
|
||||
{
|
||||
return mosquitto_loop_misc(m_mosq);
|
||||
}
|
||||
|
||||
int mosquittopp::loop_read(int max_packets)
|
||||
{
|
||||
return mosquitto_loop_read(m_mosq, max_packets);
|
||||
}
|
||||
|
||||
int mosquittopp::loop_write(int max_packets)
|
||||
{
|
||||
return mosquitto_loop_write(m_mosq, max_packets);
|
||||
}
|
||||
|
||||
int mosquittopp::loop_forever(int timeout, int max_packets)
|
||||
{
|
||||
return mosquitto_loop_forever(m_mosq, timeout, max_packets);
|
||||
}
|
||||
|
||||
int mosquittopp::loop_start()
|
||||
{
|
||||
return mosquitto_loop_start(m_mosq);
|
||||
}
|
||||
|
||||
int mosquittopp::loop_stop(bool force)
|
||||
{
|
||||
return mosquitto_loop_stop(m_mosq, force);
|
||||
}
|
||||
|
||||
bool mosquittopp::want_write()
|
||||
{
|
||||
return mosquitto_want_write(m_mosq);
|
||||
}
|
||||
|
||||
void mosquittopp::user_data_set(void *userdata)
|
||||
{
|
||||
mosquitto_user_data_set(m_mosq, userdata);
|
||||
}
|
||||
|
||||
int mosquittopp::tls_set(const char *cafile, const char *capath, const char *certfile, const char *keyfile, int (*pw_callback)(char *buf, int size, int rwflag, void *userdata))
|
||||
{
|
||||
return mosquitto_tls_set(m_mosq, cafile, capath, certfile, keyfile, pw_callback);
|
||||
}
|
||||
|
||||
int mosquittopp::tls_opts_set(int cert_reqs, const char *tls_version, const char *ciphers)
|
||||
{
|
||||
return mosquitto_tls_opts_set(m_mosq, cert_reqs, tls_version, ciphers);
|
||||
}
|
||||
|
||||
int mosquittopp::tls_insecure_set(bool value)
|
||||
{
|
||||
return mosquitto_tls_insecure_set(m_mosq, value);
|
||||
}
|
||||
|
||||
int mosquittopp::tls_psk_set(const char *psk, const char *identity, const char *ciphers)
|
||||
{
|
||||
return mosquitto_tls_psk_set(m_mosq, psk, identity, ciphers);
|
||||
}
|
||||
|
||||
}
|
||||
102
lib/cpp/mosquittopp.h
Normal file
102
lib/cpp/mosquittopp.h
Normal file
@@ -0,0 +1,102 @@
|
||||
/*
|
||||
Copyright (c) 2010-2013 Roger Light <roger@atchoo.org>
|
||||
|
||||
All rights reserved. This program and the accompanying materials
|
||||
are made available under the terms of the Eclipse Public License v1.0
|
||||
and Eclipse Distribution License v1.0 which accompany this distribution.
|
||||
|
||||
The Eclipse Public License is available at
|
||||
http://www.eclipse.org/legal/epl-v10.html
|
||||
and the Eclipse Distribution License is available at
|
||||
http://www.eclipse.org/org/documents/edl-v10.php.
|
||||
|
||||
Contributors:
|
||||
Roger Light - initial implementation and documentation.
|
||||
*/
|
||||
|
||||
#ifndef _MOSQUITTOPP_H_
|
||||
#define _MOSQUITTOPP_H_
|
||||
|
||||
#ifdef _WIN32
|
||||
# ifdef mosquittopp_EXPORTS
|
||||
# define mosqpp_EXPORT __declspec(dllexport)
|
||||
# else
|
||||
# define mosqpp_EXPORT __declspec(dllimport)
|
||||
# endif
|
||||
#else
|
||||
# define mosqpp_EXPORT
|
||||
#endif
|
||||
|
||||
#include <cstdlib>
|
||||
#include <time.h>
|
||||
#include <mosquitto.h>
|
||||
|
||||
namespace mosqpp {
|
||||
|
||||
mosqpp_EXPORT const char *strerror(int mosq_errno);
|
||||
mosqpp_EXPORT const char *connack_string(int connack_code);
|
||||
mosqpp_EXPORT int sub_topic_tokenise(const char *subtopic, char ***topics, int *count);
|
||||
mosqpp_EXPORT int sub_topic_tokens_free(char ***topics, int count);
|
||||
mosqpp_EXPORT int lib_version(int *major, int *minor, int *revision);
|
||||
mosqpp_EXPORT int lib_init();
|
||||
mosqpp_EXPORT int lib_cleanup();
|
||||
mosqpp_EXPORT int topic_matches_sub(const char *sub, const char *topic, bool *result);
|
||||
|
||||
/*
|
||||
* Class: mosquittopp
|
||||
*
|
||||
* A mosquitto client class. This is a C++ wrapper class for the mosquitto C
|
||||
* library. Please see mosquitto.h for details of the functions.
|
||||
*/
|
||||
class mosqpp_EXPORT mosquittopp {
|
||||
private:
|
||||
struct mosquitto *m_mosq;
|
||||
public:
|
||||
mosquittopp(const char *id=NULL, bool clean_session=true);
|
||||
~mosquittopp();
|
||||
|
||||
int reinitialise(const char *id, bool clean_session);
|
||||
int socket();
|
||||
int will_set(const char *topic, int payloadlen=0, const void *payload=NULL, int qos=0, bool retain=false);
|
||||
int will_clear();
|
||||
int username_pw_set(const char *username, const char *password=NULL);
|
||||
int connect(const char *host, int port=1883, int keepalive=60);
|
||||
int connect_async(const char *host, int port=1883, int keepalive=60);
|
||||
int connect(const char *host, int port, int keepalive, const char *bind_address);
|
||||
int connect_async(const char *host, int port, int keepalive, const char *bind_address);
|
||||
int reconnect();
|
||||
int reconnect_async();
|
||||
int disconnect();
|
||||
int publish(int *mid, const char *topic, int payloadlen=0, const void *payload=NULL, int qos=0, bool retain=false);
|
||||
int subscribe(int *mid, const char *sub, int qos=0);
|
||||
int unsubscribe(int *mid, const char *sub);
|
||||
void reconnect_delay_set(unsigned int reconnect_delay, unsigned int reconnect_delay_max, bool reconnect_exponential_backoff);
|
||||
int max_inflight_messages_set(unsigned int max_inflight_messages);
|
||||
void message_retry_set(unsigned int message_retry);
|
||||
void user_data_set(void *userdata);
|
||||
int tls_set(const char *cafile, const char *capath=NULL, const char *certfile=NULL, const char *keyfile=NULL, int (*pw_callback)(char *buf, int size, int rwflag, void *userdata)=NULL);
|
||||
int tls_opts_set(int cert_reqs, const char *tls_version=NULL, const char *ciphers=NULL);
|
||||
int tls_insecure_set(bool value);
|
||||
int tls_psk_set(const char *psk, const char *identity, const char *ciphers=NULL);
|
||||
|
||||
int loop(int timeout=-1, int max_packets=1);
|
||||
int loop_misc();
|
||||
int loop_read(int max_packets=1);
|
||||
int loop_write(int max_packets=1);
|
||||
int loop_forever(int timeout=-1, int max_packets=1);
|
||||
int loop_start();
|
||||
int loop_stop(bool force=false);
|
||||
bool want_write();
|
||||
|
||||
virtual void on_connect(int rc) {return;};
|
||||
virtual void on_disconnect(int rc) {return;};
|
||||
virtual void on_publish(int mid) {return;};
|
||||
virtual void on_message(const struct mosquitto_message *message) {return;};
|
||||
virtual void on_subscribe(int mid, int qos_count, const int *granted_qos) {return;};
|
||||
virtual void on_unsubscribe(int mid) {return;};
|
||||
virtual void on_log(int level, const char *str) {return;};
|
||||
virtual void on_error() {return;};
|
||||
};
|
||||
|
||||
}
|
||||
#endif
|
||||
13
lib/dummypthread.h
Normal file
13
lib/dummypthread.h
Normal file
@@ -0,0 +1,13 @@
|
||||
#ifndef _DUMMYPTHREAD_H_
|
||||
#define _DUMMYPTHREAD_H_
|
||||
|
||||
#define pthread_create(A, B, C, D)
|
||||
#define pthread_join(A, B)
|
||||
#define pthread_cancel(A)
|
||||
|
||||
#define pthread_mutex_init(A, B)
|
||||
#define pthread_mutex_destroy(A)
|
||||
#define pthread_mutex_lock(A)
|
||||
#define pthread_mutex_unlock(A)
|
||||
|
||||
#endif
|
||||
363
lib/jsws/mosquitto.js
Normal file
363
lib/jsws/mosquitto.js
Normal file
@@ -0,0 +1,363 @@
|
||||
/*
|
||||
Copyright (c) 2012 Roger Light <roger@atchoo.org>
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions are met:
|
||||
|
||||
1. Redistributions of source code must retain the above copyright notice,
|
||||
this list of conditions and the following disclaimer.
|
||||
2. Redistributions in binary form must reproduce the above copyright
|
||||
notice, this list of conditions and the following disclaimer in the
|
||||
documentation and/or other materials provided with the distribution.
|
||||
3. Neither the name of mosquitto nor the names of its
|
||||
contributors may be used to endorse or promote products derived from
|
||||
this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
|
||||
LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
/* Mosquitto MQTT Javascript/Websocket client */
|
||||
/* Provides complete support for QoS 0.
|
||||
* Will not cause an error on QoS 1/2 packets.
|
||||
*/
|
||||
|
||||
var CONNECT = 0x10;
|
||||
var CONNACK = 0x20;
|
||||
var PUBLISH = 0x30;
|
||||
var PUBACK = 0x40;
|
||||
var PUBREC = 0x50;
|
||||
var PUBREL = 0x60;
|
||||
var PUBCOMP = 0x70;
|
||||
var SUBSCRIBE = 0x80;
|
||||
var SUBACK = 0x90;
|
||||
var UNSUBSCRIBE = 0xA0;
|
||||
var UNSUBACK = 0xB0;
|
||||
var PINGREQ = 0xC0;
|
||||
var PINGRESP = 0xD0;
|
||||
var DISCONNECT = 0xE0;
|
||||
|
||||
function AB2S(buffer) {
|
||||
var binary = '';
|
||||
var bytes = new Uint8Array(buffer);
|
||||
var len = bytes.byteLength;
|
||||
for(var i=0; i<len; i++){
|
||||
binary += String.fromCharCode(bytes[i]);
|
||||
}
|
||||
return binary;
|
||||
}
|
||||
|
||||
function Mosquitto()
|
||||
{
|
||||
this.ws = null;
|
||||
this.onconnect = null;
|
||||
this.ondisconnect = null;
|
||||
this.onmessage = null;
|
||||
}
|
||||
|
||||
Mosquitto.prototype = {
|
||||
mqtt_ping : function()
|
||||
{
|
||||
var buffer = new ArrayBuffer(2);
|
||||
var i8V = new Int8Array(buffer);
|
||||
i8V[0] = PINGREQ;
|
||||
i8V[1] = 0;
|
||||
if(this.ws.readyState == 1){
|
||||
this.ws.send(buffer);
|
||||
}else{
|
||||
this.queue(buffer);
|
||||
}
|
||||
setTimeout(function(_this){_this.mqtt_ping();}, 60000, this);
|
||||
},
|
||||
|
||||
connect : function(url, keepalive){
|
||||
|
||||
this.url = url;
|
||||
this.keepalive = keepalive;
|
||||
this.mid = 1;
|
||||
this.out_queue = new Array();
|
||||
|
||||
this.ws = new WebSocket(url, 'mqttv3.1');
|
||||
this.ws.binaryType = "arraybuffer";
|
||||
this.ws.onopen = this.ws_onopen;
|
||||
this.ws.onclose = this.ws_onclose;
|
||||
this.ws.onmessage = this.ws_onmessage;
|
||||
this.ws.m = this;
|
||||
this.ws.onerror = function(evt){
|
||||
alert(evt.data);
|
||||
}
|
||||
},
|
||||
|
||||
disconnect : function(){
|
||||
if(this.ws.readyState == 1){
|
||||
var buffer = new ArrayBuffer(2);
|
||||
var i8V = new Int8Array(buffer);
|
||||
|
||||
i8V[0] = DISCONNECT;
|
||||
i8V[1] = 0;
|
||||
this.ws.send(buffer);
|
||||
this.ws.close();
|
||||
}
|
||||
},
|
||||
|
||||
ws_onopen : function(evt) {
|
||||
var buffer = new ArrayBuffer(1+1+12+2+20);
|
||||
var i8V = new Int8Array(buffer);
|
||||
|
||||
i=0;
|
||||
i8V[i++] = CONNECT;
|
||||
i8V[i++] = 12+2+20;
|
||||
i8V[i++] = 0;
|
||||
i8V[i++] = 6;
|
||||
str = "MQIsdp";
|
||||
for(var j=0; j<str.length; j++){
|
||||
i8V[i++] = str.charCodeAt(j);
|
||||
}
|
||||
i8V[i++] = 3;
|
||||
i8V[i++] = 2;
|
||||
i8V[i++] = 0;
|
||||
i8V[i++] = 60;
|
||||
i8V[i++] = 0;
|
||||
i8V[i++] = 20;
|
||||
var str = "mjsws/";
|
||||
for(var j=0; j<str.length; j++){
|
||||
i8V[i++] = str.charCodeAt(j);
|
||||
}
|
||||
var chars = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz";
|
||||
for(var j=0; j<14; j++){
|
||||
i8V[i++] = chars.charCodeAt(Math.floor(Math.random()*chars.length));
|
||||
}
|
||||
|
||||
this.send(buffer);
|
||||
while(this.m.out_queue.length > 0){
|
||||
this.send(this.m.out_queue.pop());
|
||||
}
|
||||
setTimeout(function(_this){_this.mqtt_ping();}, 60000, this.m);
|
||||
},
|
||||
|
||||
ws_onclose : function(evt) {
|
||||
if(this.m.ondisconnect){
|
||||
this.m.ondisconnect(evt.data);
|
||||
}
|
||||
},
|
||||
|
||||
ws_onmessage : function(evt) {
|
||||
var i8V = new Int8Array(evt.data);
|
||||
buffer = evt.data;
|
||||
var q=0;
|
||||
while(i8V.length > 0 && q < 1000){
|
||||
q++;
|
||||
switch(i8V[0] & 0xF0){
|
||||
case CONNACK:
|
||||
var rl = i8V[1];
|
||||
var rc = i8V[2];
|
||||
if(this.m.onconnect){
|
||||
this.m.onconnect(rc);
|
||||
}
|
||||
buffer = buffer.slice(rl+2);
|
||||
i8V = new Int8Array(buffer);
|
||||
break;
|
||||
case PUBLISH:
|
||||
var i=1;
|
||||
var mult = 1;
|
||||
var rl = 0;
|
||||
var count = 0;
|
||||
var digit;
|
||||
var qos = (i8V[0] & 0x06) >> 1;
|
||||
var retain = (i8V[0] & 0x01);
|
||||
var mid = 0;
|
||||
do{
|
||||
count++;
|
||||
digit = i8V[i++];
|
||||
rl += (digit & 127)*mult;
|
||||
mult *= 128;
|
||||
}while((digit & 128) != 0);
|
||||
|
||||
var topiclen = i8V[i++]*256 + i8V[i++];
|
||||
var atopic = buffer.slice(i, i+topiclen);
|
||||
i+=topiclen;
|
||||
var topic = AB2S(atopic);
|
||||
if(qos > 0){
|
||||
mid = i8V[i++]*256 + i8V[i++];
|
||||
}
|
||||
var apayload = buffer.slice(i, rl+count+1);
|
||||
var payload = AB2S(apayload);
|
||||
|
||||
buffer = buffer.slice(rl+1+count);
|
||||
i8V = new Int8Array(buffer);
|
||||
|
||||
if(this.m.onmessage){
|
||||
this.m.onmessage(topic, payload, qos, retain);
|
||||
}
|
||||
break;
|
||||
case PUBREC:
|
||||
case PUBREL:
|
||||
case PUBACK:
|
||||
case PUBCOMP:
|
||||
case SUBACK:
|
||||
case UNSUBACK:
|
||||
case PINGRESP:
|
||||
var rl = i8V[1];
|
||||
buffer = buffer.slice(rl+2);
|
||||
i8V = new Int8Array(buffer);
|
||||
break;
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
get_remaining_count : function(remaining_length)
|
||||
{
|
||||
if(remaining_length >= 0 && remaining_length < 128){
|
||||
return 1;
|
||||
}else if(remaining_length >= 128 && remaining_length < 16384){
|
||||
return 2;
|
||||
}else if(remaining_length >= 16384 && remaining_length < 2097152){
|
||||
return 3;
|
||||
}else if(remaining_length >= 2097152 && remaining_length < 268435456){
|
||||
return 4;
|
||||
}else{
|
||||
return -1;
|
||||
}
|
||||
},
|
||||
|
||||
generate_mid : function()
|
||||
{
|
||||
var mid = this.mid;
|
||||
this.mid++;
|
||||
if(this.mid == 256) this.mid = 0;
|
||||
return mid;
|
||||
},
|
||||
|
||||
queue : function(buffer)
|
||||
{
|
||||
this.out_queue.push(buffer);
|
||||
},
|
||||
|
||||
send_cmd_with_mid : function(cmd, mid)
|
||||
{
|
||||
var buffer = new ArrayBuffer(4);
|
||||
var i8V = new Int8Array(buffer);
|
||||
i8V[0] = cmd;
|
||||
i8V[1] = 2;
|
||||
i8V[2] = mid%128;
|
||||
i8V[3] = mid/128;
|
||||
if(this.ws.readyState == 1){
|
||||
this.ws.send(buffer);
|
||||
}else{
|
||||
this.queue(buffer);
|
||||
}
|
||||
},
|
||||
|
||||
unsubscribe : function(topic)
|
||||
{
|
||||
var rl = 2+2+topic.length;
|
||||
var remaining_count = this.get_remaining_count(rl);
|
||||
var buffer = new ArrayBuffer(1+remaining_count+rl);
|
||||
var i8V = new Int8Array(buffer);
|
||||
|
||||
var i=0;
|
||||
i8V[i++] = UNSUBSCRIBE | 0x02;
|
||||
do{
|
||||
digit = Math.floor(rl % 128);
|
||||
rl = Math.floor(rl / 128);
|
||||
if(rl > 0){
|
||||
digit = digit | 0x80;
|
||||
}
|
||||
i8V[i++] = digit;
|
||||
}while(rl > 0);
|
||||
i8V[i++] = 0;
|
||||
i8V[i++] = this.generate_mid();
|
||||
i8V[i++] = 0;
|
||||
i8V[i++] = topic.length;
|
||||
for(var j=0; j<topic.length; j++){
|
||||
i8V[i++] = topic.charCodeAt(j);
|
||||
}
|
||||
|
||||
if(this.ws.readyState == 1){
|
||||
this.ws.send(buffer);
|
||||
}else{
|
||||
this.queue(buffer);
|
||||
}
|
||||
},
|
||||
|
||||
subscribe : function(topic, qos)
|
||||
{
|
||||
if(qos != 0){
|
||||
return 1;
|
||||
}
|
||||
var rl = 2+2+topic.length+1;
|
||||
var remaining_count = this.get_remaining_count(rl);
|
||||
var buffer = new ArrayBuffer(1+remaining_count+rl);
|
||||
var i8V = new Int8Array(buffer);
|
||||
|
||||
var i=0;
|
||||
i8V[i++] = SUBSCRIBE | 0x02;
|
||||
do{
|
||||
digit = Math.floor(rl % 128);
|
||||
rl = Math.floor(rl / 128);
|
||||
if(rl > 0){
|
||||
digit = digit | 0x80;
|
||||
}
|
||||
i8V[i++] = digit;
|
||||
}while(rl > 0);
|
||||
i8V[i++] = 0;
|
||||
i8V[i++] = this.generate_mid();
|
||||
i8V[i++] = 0;
|
||||
i8V[i++] = topic.length;
|
||||
for(var j=0; j<topic.length; j++){
|
||||
i8V[i++] = topic.charCodeAt(j);
|
||||
}
|
||||
i8V[i++] = qos;
|
||||
|
||||
if(this.ws.readyState == 1){
|
||||
this.ws.send(buffer);
|
||||
}else{
|
||||
this.queue(buffer);
|
||||
}
|
||||
},
|
||||
|
||||
publish : function(topic, payload, qos, retain){
|
||||
if(qos != 0) return 1;
|
||||
var rl = 2+topic.length+payload.length;
|
||||
var remaining_count = this.get_remaining_count(rl);
|
||||
var buffer = new ArrayBuffer(1+remaining_count+rl);
|
||||
var i8V = new Int8Array(buffer);
|
||||
|
||||
var i=0;
|
||||
retain = retain?1:0;
|
||||
i8V[i++] = PUBLISH | (qos<<1) | retain;
|
||||
do{
|
||||
digit = Math.floor(rl % 128);
|
||||
rl = Math.floor(rl / 128);
|
||||
if(rl > 0){
|
||||
digit = digit | 0x80;
|
||||
}
|
||||
i8V[i++] = digit;
|
||||
}while(rl > 0);
|
||||
i8V[i++] = 0;
|
||||
i8V[i++] = topic.length;
|
||||
for(var j=0; j<topic.length; j++){
|
||||
i8V[i++] = topic.charCodeAt(j);
|
||||
}
|
||||
for(var j=0; j<payload.length; j++){
|
||||
i8V[i++] = payload.charCodeAt(j);
|
||||
}
|
||||
|
||||
if(this.ws.readyState == 1){
|
||||
this.ws.send(buffer);
|
||||
}else{
|
||||
this.queue(buffer);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
71
lib/linker.version
Normal file
71
lib/linker.version
Normal file
@@ -0,0 +1,71 @@
|
||||
/* Linker version script - currently used here primarily to control which
|
||||
* symbols are exported.
|
||||
*/
|
||||
|
||||
MOSQ_1.0 {
|
||||
global:
|
||||
mosquitto_lib_version;
|
||||
mosquitto_lib_init;
|
||||
mosquitto_lib_cleanup;
|
||||
mosquitto_new;
|
||||
mosquitto_destroy;
|
||||
mosquitto_reinitialise;
|
||||
mosquitto_will_set;
|
||||
mosquitto_will_clear;
|
||||
mosquitto_username_pw_set;
|
||||
mosquitto_connect;
|
||||
mosquitto_connect_async;
|
||||
mosquitto_reconnect;
|
||||
mosquitto_disconnect;
|
||||
mosquitto_publish;
|
||||
mosquitto_subscribe;
|
||||
mosquitto_unsubscribe;
|
||||
mosquitto_message_copy;
|
||||
mosquitto_message_free;
|
||||
mosquitto_loop;
|
||||
mosquitto_socket;
|
||||
mosquitto_loop_start;
|
||||
mosquitto_loop_stop;
|
||||
mosquitto_loop_read;
|
||||
mosquitto_loop_write;
|
||||
mosquitto_loop_misc;
|
||||
mosquitto_connect_callback_set;
|
||||
mosquitto_disconnect_callback_set;
|
||||
mosquitto_publish_callback_set;
|
||||
mosquitto_message_callback_set;
|
||||
mosquitto_subscribe_callback_set;
|
||||
mosquitto_unsubscribe_callback_set;
|
||||
mosquitto_log_callback_set;
|
||||
mosquitto_message_retry_set;
|
||||
mosquitto_want_write;
|
||||
mosquitto_user_data_set;
|
||||
mosquitto_strerror;
|
||||
mosquitto_connack_string;
|
||||
mosquitto_tls_set;
|
||||
mosquitto_tls_opts_set;
|
||||
mosquitto_tls_psk_set;
|
||||
mosquitto_sub_topic_tokenise;
|
||||
mosquitto_sub_topic_tokens_free;
|
||||
mosquitto_topic_matches_sub;
|
||||
local: *;
|
||||
};
|
||||
|
||||
MOSQ_1.1 {
|
||||
global:
|
||||
mosquitto_loop_forever;
|
||||
} MOSQ_1.0;
|
||||
|
||||
MOSQ_1.2 {
|
||||
global:
|
||||
mosquitto_connect_bind;
|
||||
mosquitto_connect_bind_async;
|
||||
mosquitto_max_inflight_messages_set;
|
||||
mosquitto_reconnect_delay_set;
|
||||
mosquitto_reconnect_async;
|
||||
mosquitto_tls_insecure_set;
|
||||
} MOSQ_1.1;
|
||||
|
||||
MOSQ_1.3 {
|
||||
global:
|
||||
mosquitto_connect_srv;
|
||||
} MOSQ_1.2;
|
||||
56
lib/logging_mosq.c
Normal file
56
lib/logging_mosq.c
Normal file
@@ -0,0 +1,56 @@
|
||||
/*
|
||||
Copyright (c) 2009-2014 Roger Light <roger@atchoo.org>
|
||||
|
||||
All rights reserved. This program and the accompanying materials
|
||||
are made available under the terms of the Eclipse Public License v1.0
|
||||
and Eclipse Distribution License v1.0 which accompany this distribution.
|
||||
|
||||
The Eclipse Public License is available at
|
||||
http://www.eclipse.org/legal/epl-v10.html
|
||||
and the Eclipse Distribution License is available at
|
||||
http://www.eclipse.org/org/documents/edl-v10.php.
|
||||
|
||||
Contributors:
|
||||
Roger Light - initial implementation and documentation.
|
||||
*/
|
||||
#include <assert.h>
|
||||
#include <stdarg.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
|
||||
#include <mosquitto_internal.h>
|
||||
#include <mosquitto.h>
|
||||
#include <memory_mosq.h>
|
||||
|
||||
int _mosquitto_log_printf(struct mosquitto *mosq, int priority, const char *fmt, ...)
|
||||
{
|
||||
va_list va;
|
||||
char *s;
|
||||
int len;
|
||||
|
||||
assert(mosq);
|
||||
assert(fmt);
|
||||
|
||||
pthread_mutex_lock(&mosq->log_callback_mutex);
|
||||
if(mosq->on_log){
|
||||
len = strlen(fmt) + 500;
|
||||
s = _mosquitto_malloc(len*sizeof(char));
|
||||
if(!s){
|
||||
pthread_mutex_unlock(&mosq->log_callback_mutex);
|
||||
return MOSQ_ERR_NOMEM;
|
||||
}
|
||||
|
||||
va_start(va, fmt);
|
||||
vsnprintf(s, len, fmt, va);
|
||||
va_end(va);
|
||||
s[len-1] = '\0'; /* Ensure string is null terminated. */
|
||||
|
||||
mosq->on_log(mosq, mosq->userdata, priority, s);
|
||||
|
||||
_mosquitto_free(s);
|
||||
}
|
||||
pthread_mutex_unlock(&mosq->log_callback_mutex);
|
||||
|
||||
return MOSQ_ERR_SUCCESS;
|
||||
}
|
||||
|
||||
23
lib/logging_mosq.h
Normal file
23
lib/logging_mosq.h
Normal file
@@ -0,0 +1,23 @@
|
||||
/*
|
||||
Copyright (c) 2009-2014 Roger Light <roger@atchoo.org>
|
||||
|
||||
All rights reserved. This program and the accompanying materials
|
||||
are made available under the terms of the Eclipse Public License v1.0
|
||||
and Eclipse Distribution License v1.0 which accompany this distribution.
|
||||
|
||||
The Eclipse Public License is available at
|
||||
http://www.eclipse.org/legal/epl-v10.html
|
||||
and the Eclipse Distribution License is available at
|
||||
http://www.eclipse.org/org/documents/edl-v10.php.
|
||||
|
||||
Contributors:
|
||||
Roger Light - initial implementation and documentation.
|
||||
*/
|
||||
#ifndef _LOGGING_MOSQ_H_
|
||||
#define _LOGGING_MOSQ_H_
|
||||
|
||||
#include <mosquitto.h>
|
||||
|
||||
int _mosquitto_log_printf(struct mosquitto *mosq, int priority, const char *fmt, ...);
|
||||
|
||||
#endif
|
||||
121
lib/memory_mosq.c
Normal file
121
lib/memory_mosq.c
Normal file
@@ -0,0 +1,121 @@
|
||||
/*
|
||||
Copyright (c) 2009-2014 Roger Light <roger@atchoo.org>
|
||||
|
||||
All rights reserved. This program and the accompanying materials
|
||||
are made available under the terms of the Eclipse Public License v1.0
|
||||
and Eclipse Distribution License v1.0 which accompany this distribution.
|
||||
|
||||
The Eclipse Public License is available at
|
||||
http://www.eclipse.org/legal/epl-v10.html
|
||||
and the Eclipse Distribution License is available at
|
||||
http://www.eclipse.org/org/documents/edl-v10.php.
|
||||
|
||||
Contributors:
|
||||
Roger Light - initial implementation and documentation.
|
||||
*/
|
||||
|
||||
#include <config.h>
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
#include <memory_mosq.h>
|
||||
|
||||
#ifdef REAL_WITH_MEMORY_TRACKING
|
||||
# if defined(__APPLE__)
|
||||
# include <malloc/malloc.h>
|
||||
# define malloc_usable_size malloc_size
|
||||
# elif defined(__FreeBSD__)
|
||||
# include <malloc_np.h>
|
||||
# else
|
||||
# include <malloc.h>
|
||||
# endif
|
||||
#endif
|
||||
|
||||
#ifdef REAL_WITH_MEMORY_TRACKING
|
||||
static unsigned long memcount = 0;
|
||||
static unsigned long max_memcount = 0;
|
||||
#endif
|
||||
|
||||
void *_mosquitto_calloc(size_t nmemb, size_t size)
|
||||
{
|
||||
void *mem = calloc(nmemb, size);
|
||||
|
||||
#ifdef REAL_WITH_MEMORY_TRACKING
|
||||
memcount += malloc_usable_size(mem);
|
||||
if(memcount > max_memcount){
|
||||
max_memcount = memcount;
|
||||
}
|
||||
#endif
|
||||
|
||||
return mem;
|
||||
}
|
||||
|
||||
void _mosquitto_free(void *mem)
|
||||
{
|
||||
#ifdef REAL_WITH_MEMORY_TRACKING
|
||||
memcount -= malloc_usable_size(mem);
|
||||
#endif
|
||||
free(mem);
|
||||
}
|
||||
|
||||
void *_mosquitto_malloc(size_t size)
|
||||
{
|
||||
void *mem = malloc(size);
|
||||
|
||||
#ifdef REAL_WITH_MEMORY_TRACKING
|
||||
memcount += malloc_usable_size(mem);
|
||||
if(memcount > max_memcount){
|
||||
max_memcount = memcount;
|
||||
}
|
||||
#endif
|
||||
|
||||
return mem;
|
||||
}
|
||||
|
||||
#ifdef REAL_WITH_MEMORY_TRACKING
|
||||
unsigned long _mosquitto_memory_used(void)
|
||||
{
|
||||
return memcount;
|
||||
}
|
||||
|
||||
unsigned long _mosquitto_max_memory_used(void)
|
||||
{
|
||||
return max_memcount;
|
||||
}
|
||||
#endif
|
||||
|
||||
void *_mosquitto_realloc(void *ptr, size_t size)
|
||||
{
|
||||
void *mem;
|
||||
#ifdef REAL_WITH_MEMORY_TRACKING
|
||||
if(ptr){
|
||||
memcount -= malloc_usable_size(ptr);
|
||||
}
|
||||
#endif
|
||||
mem = realloc(ptr, size);
|
||||
|
||||
#ifdef REAL_WITH_MEMORY_TRACKING
|
||||
memcount += malloc_usable_size(mem);
|
||||
if(memcount > max_memcount){
|
||||
max_memcount = memcount;
|
||||
}
|
||||
#endif
|
||||
|
||||
return mem;
|
||||
}
|
||||
|
||||
char *_mosquitto_strdup(const char *s)
|
||||
{
|
||||
char *str = strdup(s);
|
||||
|
||||
#ifdef REAL_WITH_MEMORY_TRACKING
|
||||
memcount += malloc_usable_size(str);
|
||||
if(memcount > max_memcount){
|
||||
max_memcount = memcount;
|
||||
}
|
||||
#endif
|
||||
|
||||
return str;
|
||||
}
|
||||
|
||||
37
lib/memory_mosq.h
Normal file
37
lib/memory_mosq.h
Normal file
@@ -0,0 +1,37 @@
|
||||
/*
|
||||
Copyright (c) 2010-2014 Roger Light <roger@atchoo.org>
|
||||
|
||||
All rights reserved. This program and the accompanying materials
|
||||
are made available under the terms of the Eclipse Public License v1.0
|
||||
and Eclipse Distribution License v1.0 which accompany this distribution.
|
||||
|
||||
The Eclipse Public License is available at
|
||||
http://www.eclipse.org/legal/epl-v10.html
|
||||
and the Eclipse Distribution License is available at
|
||||
http://www.eclipse.org/org/documents/edl-v10.php.
|
||||
|
||||
Contributors:
|
||||
Roger Light - initial implementation and documentation.
|
||||
*/
|
||||
|
||||
#ifndef _MEMORY_MOSQ_H_
|
||||
#define _MEMORY_MOSQ_H_
|
||||
|
||||
#include <stdio.h>
|
||||
#include <sys/types.h>
|
||||
|
||||
#if defined(WITH_MEMORY_TRACKING) && defined(WITH_BROKER) && !defined(WIN32) && !defined(__SYMBIAN32__)
|
||||
#define REAL_WITH_MEMORY_TRACKING
|
||||
#endif
|
||||
|
||||
void *_mosquitto_calloc(size_t nmemb, size_t size);
|
||||
void _mosquitto_free(void *mem);
|
||||
void *_mosquitto_malloc(size_t size);
|
||||
#ifdef REAL_WITH_MEMORY_TRACKING
|
||||
unsigned long _mosquitto_memory_used(void);
|
||||
unsigned long _mosquitto_max_memory_used(void);
|
||||
#endif
|
||||
void *_mosquitto_realloc(void *ptr, size_t size);
|
||||
char *_mosquitto_strdup(const char *s);
|
||||
|
||||
#endif
|
||||
387
lib/messages_mosq.c
Normal file
387
lib/messages_mosq.c
Normal file
@@ -0,0 +1,387 @@
|
||||
/*
|
||||
Copyright (c) 2010-2014 Roger Light <roger@atchoo.org>
|
||||
|
||||
All rights reserved. This program and the accompanying materials
|
||||
are made available under the terms of the Eclipse Public License v1.0
|
||||
and Eclipse Distribution License v1.0 which accompany this distribution.
|
||||
|
||||
The Eclipse Public License is available at
|
||||
http://www.eclipse.org/legal/epl-v10.html
|
||||
and the Eclipse Distribution License is available at
|
||||
http://www.eclipse.org/org/documents/edl-v10.php.
|
||||
|
||||
Contributors:
|
||||
Roger Light - initial implementation and documentation.
|
||||
*/
|
||||
|
||||
#include <assert.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
#include <mosquitto_internal.h>
|
||||
#include <mosquitto.h>
|
||||
#include <memory_mosq.h>
|
||||
#include <messages_mosq.h>
|
||||
#include <send_mosq.h>
|
||||
#include <time_mosq.h>
|
||||
|
||||
void _mosquitto_message_cleanup(struct mosquitto_message_all **message)
|
||||
{
|
||||
struct mosquitto_message_all *msg;
|
||||
|
||||
if(!message || !*message) return;
|
||||
|
||||
msg = *message;
|
||||
|
||||
if(msg->msg.topic) _mosquitto_free(msg->msg.topic);
|
||||
if(msg->msg.payload) _mosquitto_free(msg->msg.payload);
|
||||
_mosquitto_free(msg);
|
||||
}
|
||||
|
||||
void _mosquitto_message_cleanup_all(struct mosquitto *mosq)
|
||||
{
|
||||
struct mosquitto_message_all *tmp;
|
||||
|
||||
assert(mosq);
|
||||
|
||||
while(mosq->in_messages){
|
||||
tmp = mosq->in_messages->next;
|
||||
_mosquitto_message_cleanup(&mosq->in_messages);
|
||||
mosq->in_messages = tmp;
|
||||
}
|
||||
while(mosq->out_messages){
|
||||
tmp = mosq->out_messages->next;
|
||||
_mosquitto_message_cleanup(&mosq->out_messages);
|
||||
mosq->out_messages = tmp;
|
||||
}
|
||||
}
|
||||
|
||||
int mosquitto_message_copy(struct mosquitto_message *dst, const struct mosquitto_message *src)
|
||||
{
|
||||
if(!dst || !src) return MOSQ_ERR_INVAL;
|
||||
|
||||
dst->mid = src->mid;
|
||||
dst->topic = _mosquitto_strdup(src->topic);
|
||||
if(!dst->topic) return MOSQ_ERR_NOMEM;
|
||||
dst->qos = src->qos;
|
||||
dst->retain = src->retain;
|
||||
if(src->payloadlen){
|
||||
dst->payload = _mosquitto_malloc(src->payloadlen);
|
||||
if(!dst->payload){
|
||||
_mosquitto_free(dst->topic);
|
||||
return MOSQ_ERR_NOMEM;
|
||||
}
|
||||
memcpy(dst->payload, src->payload, src->payloadlen);
|
||||
dst->payloadlen = src->payloadlen;
|
||||
}else{
|
||||
dst->payloadlen = 0;
|
||||
dst->payload = NULL;
|
||||
}
|
||||
return MOSQ_ERR_SUCCESS;
|
||||
}
|
||||
|
||||
int _mosquitto_message_delete(struct mosquitto *mosq, uint16_t mid, enum mosquitto_msg_direction dir)
|
||||
{
|
||||
struct mosquitto_message_all *message;
|
||||
int rc;
|
||||
assert(mosq);
|
||||
|
||||
rc = _mosquitto_message_remove(mosq, mid, dir, &message);
|
||||
if(rc == MOSQ_ERR_SUCCESS){
|
||||
_mosquitto_message_cleanup(&message);
|
||||
}
|
||||
return rc;
|
||||
}
|
||||
|
||||
void mosquitto_message_free(struct mosquitto_message **message)
|
||||
{
|
||||
struct mosquitto_message *msg;
|
||||
|
||||
if(!message || !*message) return;
|
||||
|
||||
msg = *message;
|
||||
|
||||
if(msg->topic) _mosquitto_free(msg->topic);
|
||||
if(msg->payload) _mosquitto_free(msg->payload);
|
||||
_mosquitto_free(msg);
|
||||
}
|
||||
|
||||
void _mosquitto_message_queue(struct mosquitto *mosq, struct mosquitto_message_all *message, enum mosquitto_msg_direction dir)
|
||||
{
|
||||
/* mosq->*_message_mutex should be locked before entering this function */
|
||||
assert(mosq);
|
||||
assert(message);
|
||||
|
||||
if(dir == mosq_md_out){
|
||||
mosq->out_queue_len++;
|
||||
message->next = NULL;
|
||||
if(mosq->out_messages_last){
|
||||
mosq->out_messages_last->next = message;
|
||||
}else{
|
||||
mosq->out_messages = message;
|
||||
}
|
||||
mosq->out_messages_last = message;
|
||||
}else{
|
||||
mosq->in_queue_len++;
|
||||
if(message->msg.qos > 0 && (mosq->max_inflight_messages == 0 || mosq->inflight_messages < mosq->max_inflight_messages)){
|
||||
mosq->inflight_messages++;
|
||||
}
|
||||
message->next = NULL;
|
||||
if(mosq->in_messages_last){
|
||||
mosq->in_messages_last->next = message;
|
||||
}else{
|
||||
mosq->in_messages = message;
|
||||
}
|
||||
mosq->in_messages_last = message;
|
||||
}
|
||||
}
|
||||
|
||||
void _mosquitto_messages_reconnect_reset(struct mosquitto *mosq)
|
||||
{
|
||||
struct mosquitto_message_all *message;
|
||||
struct mosquitto_message_all *prev = NULL;
|
||||
assert(mosq);
|
||||
|
||||
pthread_mutex_lock(&mosq->in_message_mutex);
|
||||
message = mosq->in_messages;
|
||||
mosq->in_queue_len = 0;
|
||||
while(message){
|
||||
mosq->in_queue_len++;
|
||||
message->timestamp = 0;
|
||||
if(message->msg.qos != 2){
|
||||
if(prev){
|
||||
prev->next = message->next;
|
||||
_mosquitto_message_cleanup(&message);
|
||||
message = prev;
|
||||
}else{
|
||||
mosq->in_messages = message->next;
|
||||
_mosquitto_message_cleanup(&message);
|
||||
message = mosq->in_messages;
|
||||
}
|
||||
}else{
|
||||
/* Message state can be preserved here because it should match
|
||||
* whatever the client has got. */
|
||||
}
|
||||
prev = message;
|
||||
message = message->next;
|
||||
}
|
||||
mosq->in_messages_last = prev;
|
||||
pthread_mutex_unlock(&mosq->in_message_mutex);
|
||||
|
||||
|
||||
pthread_mutex_lock(&mosq->out_message_mutex);
|
||||
mosq->inflight_messages = 0;
|
||||
message = mosq->out_messages;
|
||||
mosq->out_queue_len = 0;
|
||||
while(message){
|
||||
mosq->out_queue_len++;
|
||||
message->timestamp = 0;
|
||||
|
||||
if(message->msg.qos > 0){
|
||||
mosq->inflight_messages++;
|
||||
}
|
||||
if(mosq->max_inflight_messages == 0 || mosq->inflight_messages < mosq->max_inflight_messages){
|
||||
if(message->msg.qos == 1){
|
||||
message->state = mosq_ms_wait_for_puback;
|
||||
}else if(message->msg.qos == 2){
|
||||
/* Should be able to preserve state. */
|
||||
}
|
||||
}else{
|
||||
message->state = mosq_ms_invalid;
|
||||
}
|
||||
prev = message;
|
||||
message = message->next;
|
||||
}
|
||||
mosq->out_messages_last = prev;
|
||||
pthread_mutex_unlock(&mosq->out_message_mutex);
|
||||
}
|
||||
|
||||
int _mosquitto_message_remove(struct mosquitto *mosq, uint16_t mid, enum mosquitto_msg_direction dir, struct mosquitto_message_all **message)
|
||||
{
|
||||
struct mosquitto_message_all *cur, *prev = NULL;
|
||||
bool found = false;
|
||||
int rc;
|
||||
assert(mosq);
|
||||
assert(message);
|
||||
|
||||
if(dir == mosq_md_out){
|
||||
pthread_mutex_lock(&mosq->out_message_mutex);
|
||||
cur = mosq->out_messages;
|
||||
while(cur){
|
||||
if(cur->msg.mid == mid){
|
||||
if(prev){
|
||||
prev->next = cur->next;
|
||||
}else{
|
||||
mosq->out_messages = cur->next;
|
||||
}
|
||||
*message = cur;
|
||||
mosq->out_queue_len--;
|
||||
if(cur->next == NULL){
|
||||
mosq->out_messages_last = prev;
|
||||
}else if(!mosq->out_messages){
|
||||
mosq->out_messages_last = NULL;
|
||||
}
|
||||
if(cur->msg.qos > 0){
|
||||
mosq->inflight_messages--;
|
||||
}
|
||||
found = true;
|
||||
break;
|
||||
}
|
||||
prev = cur;
|
||||
cur = cur->next;
|
||||
}
|
||||
|
||||
if(found){
|
||||
cur = mosq->out_messages;
|
||||
while(cur){
|
||||
if(mosq->max_inflight_messages == 0 || mosq->inflight_messages < mosq->max_inflight_messages){
|
||||
if(cur->msg.qos > 0 && cur->state == mosq_ms_invalid){
|
||||
mosq->inflight_messages++;
|
||||
if(cur->msg.qos == 1){
|
||||
cur->state = mosq_ms_wait_for_puback;
|
||||
}else if(cur->msg.qos == 2){
|
||||
cur->state = mosq_ms_wait_for_pubrec;
|
||||
}
|
||||
rc = _mosquitto_send_publish(mosq, cur->msg.mid, cur->msg.topic, cur->msg.payloadlen, cur->msg.payload, cur->msg.qos, cur->msg.retain, cur->dup);
|
||||
if(rc){
|
||||
pthread_mutex_unlock(&mosq->out_message_mutex);
|
||||
return rc;
|
||||
}
|
||||
}
|
||||
}else{
|
||||
pthread_mutex_unlock(&mosq->out_message_mutex);
|
||||
return MOSQ_ERR_SUCCESS;
|
||||
}
|
||||
cur = cur->next;
|
||||
}
|
||||
pthread_mutex_unlock(&mosq->out_message_mutex);
|
||||
return MOSQ_ERR_SUCCESS;
|
||||
}else{
|
||||
pthread_mutex_unlock(&mosq->out_message_mutex);
|
||||
return MOSQ_ERR_NOT_FOUND;
|
||||
}
|
||||
}else{
|
||||
pthread_mutex_lock(&mosq->in_message_mutex);
|
||||
cur = mosq->in_messages;
|
||||
while(cur){
|
||||
if(cur->msg.mid == mid){
|
||||
if(prev){
|
||||
prev->next = cur->next;
|
||||
}else{
|
||||
mosq->in_messages = cur->next;
|
||||
}
|
||||
*message = cur;
|
||||
mosq->in_queue_len--;
|
||||
if(cur->next == NULL){
|
||||
mosq->in_messages_last = prev;
|
||||
}else if(!mosq->in_messages){
|
||||
mosq->in_messages_last = NULL;
|
||||
}
|
||||
if(cur->msg.qos == 2){
|
||||
mosq->inflight_messages--;
|
||||
}
|
||||
found = true;
|
||||
break;
|
||||
}
|
||||
prev = cur;
|
||||
cur = cur->next;
|
||||
}
|
||||
|
||||
pthread_mutex_unlock(&mosq->in_message_mutex);
|
||||
if(found){
|
||||
return MOSQ_ERR_SUCCESS;
|
||||
}else{
|
||||
return MOSQ_ERR_NOT_FOUND;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef WITH_THREADING
|
||||
void _mosquitto_message_retry_check_actual(struct mosquitto *mosq, struct mosquitto_message_all *messages, pthread_mutex_t mutex)
|
||||
#else
|
||||
void _mosquitto_message_retry_check_actual(struct mosquitto *mosq, struct mosquitto_message_all *messages)
|
||||
#endif
|
||||
{
|
||||
time_t now = mosquitto_time();
|
||||
assert(mosq);
|
||||
|
||||
#ifdef WITH_THREADING
|
||||
pthread_mutex_lock(&mutex);
|
||||
#endif
|
||||
|
||||
while(messages){
|
||||
if(messages->timestamp + mosq->message_retry < now){
|
||||
switch(messages->state){
|
||||
case mosq_ms_wait_for_puback:
|
||||
case mosq_ms_wait_for_pubrec:
|
||||
messages->timestamp = now;
|
||||
messages->dup = true;
|
||||
_mosquitto_send_publish(mosq, messages->msg.mid, messages->msg.topic, messages->msg.payloadlen, messages->msg.payload, messages->msg.qos, messages->msg.retain, messages->dup);
|
||||
break;
|
||||
case mosq_ms_wait_for_pubrel:
|
||||
messages->timestamp = now;
|
||||
messages->dup = true;
|
||||
_mosquitto_send_pubrec(mosq, messages->msg.mid);
|
||||
break;
|
||||
case mosq_ms_wait_for_pubcomp:
|
||||
messages->timestamp = now;
|
||||
messages->dup = true;
|
||||
_mosquitto_send_pubrel(mosq, messages->msg.mid, true);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
messages = messages->next;
|
||||
}
|
||||
#ifdef WITH_THREADING
|
||||
pthread_mutex_unlock(&mutex);
|
||||
#endif
|
||||
}
|
||||
|
||||
void _mosquitto_message_retry_check(struct mosquitto *mosq)
|
||||
{
|
||||
#ifdef WITH_THREADING
|
||||
_mosquitto_message_retry_check_actual(mosq, mosq->out_messages, mosq->out_message_mutex);
|
||||
_mosquitto_message_retry_check_actual(mosq, mosq->in_messages, mosq->in_message_mutex);
|
||||
#else
|
||||
_mosquitto_message_retry_check_actual(mosq, mosq->out_messages);
|
||||
_mosquitto_message_retry_check_actual(mosq, mosq->in_messages);
|
||||
#endif
|
||||
}
|
||||
|
||||
void mosquitto_message_retry_set(struct mosquitto *mosq, unsigned int message_retry)
|
||||
{
|
||||
assert(mosq);
|
||||
if(mosq) mosq->message_retry = message_retry;
|
||||
}
|
||||
|
||||
int _mosquitto_message_out_update(struct mosquitto *mosq, uint16_t mid, enum mosquitto_msg_state state)
|
||||
{
|
||||
struct mosquitto_message_all *message;
|
||||
assert(mosq);
|
||||
|
||||
pthread_mutex_lock(&mosq->out_message_mutex);
|
||||
message = mosq->out_messages;
|
||||
while(message){
|
||||
if(message->msg.mid == mid){
|
||||
message->state = state;
|
||||
message->timestamp = mosquitto_time();
|
||||
pthread_mutex_unlock(&mosq->out_message_mutex);
|
||||
return MOSQ_ERR_SUCCESS;
|
||||
}
|
||||
message = message->next;
|
||||
}
|
||||
pthread_mutex_unlock(&mosq->out_message_mutex);
|
||||
return MOSQ_ERR_NOT_FOUND;
|
||||
}
|
||||
|
||||
int mosquitto_max_inflight_messages_set(struct mosquitto *mosq, unsigned int max_inflight_messages)
|
||||
{
|
||||
if(!mosq) return MOSQ_ERR_INVAL;
|
||||
|
||||
mosq->max_inflight_messages = max_inflight_messages;
|
||||
|
||||
return MOSQ_ERR_SUCCESS;
|
||||
}
|
||||
|
||||
31
lib/messages_mosq.h
Normal file
31
lib/messages_mosq.h
Normal file
@@ -0,0 +1,31 @@
|
||||
/*
|
||||
Copyright (c) 2010-2014 Roger Light <roger@atchoo.org>
|
||||
|
||||
All rights reserved. This program and the accompanying materials
|
||||
are made available under the terms of the Eclipse Public License v1.0
|
||||
and Eclipse Distribution License v1.0 which accompany this distribution.
|
||||
|
||||
The Eclipse Public License is available at
|
||||
http://www.eclipse.org/legal/epl-v10.html
|
||||
and the Eclipse Distribution License is available at
|
||||
http://www.eclipse.org/org/documents/edl-v10.php.
|
||||
|
||||
Contributors:
|
||||
Roger Light - initial implementation and documentation.
|
||||
*/
|
||||
#ifndef _MESSAGES_MOSQ_H_
|
||||
#define _MESSAGES_MOSQ_H_
|
||||
|
||||
#include <mosquitto_internal.h>
|
||||
#include <mosquitto.h>
|
||||
|
||||
void _mosquitto_message_cleanup_all(struct mosquitto *mosq);
|
||||
void _mosquitto_message_cleanup(struct mosquitto_message_all **message);
|
||||
int _mosquitto_message_delete(struct mosquitto *mosq, uint16_t mid, enum mosquitto_msg_direction dir);
|
||||
void _mosquitto_message_queue(struct mosquitto *mosq, struct mosquitto_message_all *message, enum mosquitto_msg_direction dir);
|
||||
void _mosquitto_messages_reconnect_reset(struct mosquitto *mosq);
|
||||
int _mosquitto_message_remove(struct mosquitto *mosq, uint16_t mid, enum mosquitto_msg_direction dir, struct mosquitto_message_all **message);
|
||||
void _mosquitto_message_retry_check(struct mosquitto *mosq);
|
||||
int _mosquitto_message_out_update(struct mosquitto *mosq, uint16_t mid, enum mosquitto_msg_state state);
|
||||
|
||||
#endif
|
||||
1293
lib/mosquitto.c
Normal file
1293
lib/mosquitto.c
Normal file
File diff suppressed because it is too large
Load Diff
1409
lib/mosquitto.h
Normal file
1409
lib/mosquitto.h
Normal file
File diff suppressed because it is too large
Load Diff
230
lib/mosquitto_internal.h
Normal file
230
lib/mosquitto_internal.h
Normal file
@@ -0,0 +1,230 @@
|
||||
/*
|
||||
Copyright (c) 2010-2014 Roger Light <roger@atchoo.org>
|
||||
|
||||
All rights reserved. This program and the accompanying materials
|
||||
are made available under the terms of the Eclipse Public License v1.0
|
||||
and Eclipse Distribution License v1.0 which accompany this distribution.
|
||||
|
||||
The Eclipse Public License is available at
|
||||
http://www.eclipse.org/legal/epl-v10.html
|
||||
and the Eclipse Distribution License is available at
|
||||
http://www.eclipse.org/org/documents/edl-v10.php.
|
||||
|
||||
Contributors:
|
||||
Roger Light - initial implementation and documentation.
|
||||
*/
|
||||
|
||||
#ifndef _MOSQUITTO_INTERNAL_H_
|
||||
#define _MOSQUITTO_INTERNAL_H_
|
||||
|
||||
#include <config.h>
|
||||
|
||||
#ifdef WIN32
|
||||
# include <winsock2.h>
|
||||
#endif
|
||||
|
||||
#ifdef WITH_TLS
|
||||
#include <openssl/ssl.h>
|
||||
#endif
|
||||
#include <stdlib.h>
|
||||
|
||||
#if defined(WITH_THREADING) && !defined(WITH_BROKER)
|
||||
# include <pthread.h>
|
||||
#else
|
||||
# include <dummypthread.h>
|
||||
#endif
|
||||
|
||||
#ifdef WITH_SRV
|
||||
# include <ares.h>
|
||||
#endif
|
||||
|
||||
#ifdef WIN32
|
||||
# if _MSC_VER < 1600
|
||||
typedef unsigned char uint8_t;
|
||||
typedef unsigned short uint16_t;
|
||||
typedef unsigned int uint32_t;
|
||||
typedef unsigned long long uint64_t;
|
||||
# else
|
||||
# include <stdint.h>
|
||||
# endif
|
||||
#else
|
||||
# include <stdint.h>
|
||||
#endif
|
||||
|
||||
#include "mosquitto.h"
|
||||
#include "time_mosq.h"
|
||||
#ifdef WITH_BROKER
|
||||
struct mosquitto_client_msg;
|
||||
#endif
|
||||
|
||||
enum mosquitto_msg_direction {
|
||||
mosq_md_in = 0,
|
||||
mosq_md_out = 1
|
||||
};
|
||||
|
||||
enum mosquitto_msg_state {
|
||||
mosq_ms_invalid = 0,
|
||||
mosq_ms_publish_qos0 = 1,
|
||||
mosq_ms_publish_qos1 = 2,
|
||||
mosq_ms_wait_for_puback = 3,
|
||||
mosq_ms_publish_qos2 = 4,
|
||||
mosq_ms_wait_for_pubrec = 5,
|
||||
mosq_ms_resend_pubrel = 6,
|
||||
mosq_ms_wait_for_pubrel = 7,
|
||||
mosq_ms_resend_pubcomp = 8,
|
||||
mosq_ms_wait_for_pubcomp = 9,
|
||||
mosq_ms_send_pubrec = 10,
|
||||
mosq_ms_queued = 11
|
||||
};
|
||||
|
||||
enum mosquitto_client_state {
|
||||
mosq_cs_new = 0,
|
||||
mosq_cs_connected = 1,
|
||||
mosq_cs_disconnecting = 2,
|
||||
mosq_cs_connect_async = 3,
|
||||
mosq_cs_connect_pending = 4,
|
||||
mosq_cs_connect_srv = 5
|
||||
};
|
||||
|
||||
enum _mosquitto_protocol {
|
||||
mosq_p_invalid = 0,
|
||||
mosq_p_mqtt31 = 1,
|
||||
mosq_p_mqtt311 = 2,
|
||||
mosq_p_mqtts = 3
|
||||
};
|
||||
|
||||
enum _mosquitto_transport {
|
||||
mosq_t_invalid = 0,
|
||||
mosq_t_tcp = 1,
|
||||
mosq_t_ws = 2,
|
||||
mosq_t_sctp = 3
|
||||
};
|
||||
|
||||
struct _mosquitto_packet{
|
||||
uint8_t command;
|
||||
uint8_t have_remaining;
|
||||
uint8_t remaining_count;
|
||||
uint16_t mid;
|
||||
uint32_t remaining_mult;
|
||||
uint32_t remaining_length;
|
||||
uint32_t packet_length;
|
||||
uint32_t to_process;
|
||||
uint32_t pos;
|
||||
uint8_t *payload;
|
||||
struct _mosquitto_packet *next;
|
||||
};
|
||||
|
||||
struct mosquitto_message_all{
|
||||
struct mosquitto_message_all *next;
|
||||
time_t timestamp;
|
||||
//enum mosquitto_msg_direction direction;
|
||||
enum mosquitto_msg_state state;
|
||||
bool dup;
|
||||
struct mosquitto_message msg;
|
||||
};
|
||||
|
||||
struct mosquitto {
|
||||
#ifndef WIN32
|
||||
int sock;
|
||||
# ifndef WITH_BROKER
|
||||
int sockpairR, sockpairW;
|
||||
# endif
|
||||
#else
|
||||
SOCKET sock;
|
||||
# ifndef WITH_BROKER
|
||||
SOCKET sockpairR, sockpairW;
|
||||
# endif
|
||||
#endif
|
||||
enum _mosquitto_protocol protocol;
|
||||
char *address;
|
||||
char *id;
|
||||
char *username;
|
||||
char *password;
|
||||
uint16_t keepalive;
|
||||
bool clean_session;
|
||||
enum mosquitto_client_state state;
|
||||
time_t last_msg_in;
|
||||
time_t last_msg_out;
|
||||
time_t ping_t;
|
||||
uint16_t last_mid;
|
||||
struct _mosquitto_packet in_packet;
|
||||
struct _mosquitto_packet *current_out_packet;
|
||||
struct _mosquitto_packet *out_packet;
|
||||
struct mosquitto_message *will;
|
||||
#ifdef WITH_TLS
|
||||
SSL *ssl;
|
||||
SSL_CTX *ssl_ctx;
|
||||
char *tls_cafile;
|
||||
char *tls_capath;
|
||||
char *tls_certfile;
|
||||
char *tls_keyfile;
|
||||
int (*tls_pw_callback)(char *buf, int size, int rwflag, void *userdata);
|
||||
int tls_cert_reqs;
|
||||
char *tls_version;
|
||||
char *tls_ciphers;
|
||||
char *tls_psk;
|
||||
char *tls_psk_identity;
|
||||
bool tls_insecure;
|
||||
#endif
|
||||
bool want_write;
|
||||
#if defined(WITH_THREADING) && !defined(WITH_BROKER)
|
||||
pthread_mutex_t callback_mutex;
|
||||
pthread_mutex_t log_callback_mutex;
|
||||
pthread_mutex_t msgtime_mutex;
|
||||
pthread_mutex_t out_packet_mutex;
|
||||
pthread_mutex_t current_out_packet_mutex;
|
||||
pthread_mutex_t state_mutex;
|
||||
pthread_mutex_t in_message_mutex;
|
||||
pthread_mutex_t out_message_mutex;
|
||||
pthread_t thread_id;
|
||||
#endif
|
||||
#ifdef WITH_BROKER
|
||||
bool is_bridge;
|
||||
struct _mqtt3_bridge *bridge;
|
||||
struct mosquitto_client_msg *msgs;
|
||||
struct mosquitto_client_msg *last_msg;
|
||||
int msg_count;
|
||||
int msg_count12;
|
||||
struct _mosquitto_acl_user *acl_list;
|
||||
struct _mqtt3_listener *listener;
|
||||
time_t disconnect_t;
|
||||
int pollfd_index;
|
||||
int db_index;
|
||||
struct _mosquitto_packet *out_packet_last;
|
||||
bool is_dropping;
|
||||
#else
|
||||
void *userdata;
|
||||
bool in_callback;
|
||||
unsigned int message_retry;
|
||||
time_t last_retry_check;
|
||||
struct mosquitto_message_all *in_messages;
|
||||
struct mosquitto_message_all *in_messages_last;
|
||||
struct mosquitto_message_all *out_messages;
|
||||
struct mosquitto_message_all *out_messages_last;
|
||||
void (*on_connect)(struct mosquitto *, void *userdata, int rc);
|
||||
void (*on_disconnect)(struct mosquitto *, void *userdata, int rc);
|
||||
void (*on_publish)(struct mosquitto *, void *userdata, int mid);
|
||||
void (*on_message)(struct mosquitto *, void *userdata, const struct mosquitto_message *message);
|
||||
void (*on_subscribe)(struct mosquitto *, void *userdata, int mid, int qos_count, const int *granted_qos);
|
||||
void (*on_unsubscribe)(struct mosquitto *, void *userdata, int mid);
|
||||
void (*on_log)(struct mosquitto *, void *userdata, int level, const char *str);
|
||||
//void (*on_error)();
|
||||
char *host;
|
||||
int port;
|
||||
int in_queue_len;
|
||||
int out_queue_len;
|
||||
char *bind_address;
|
||||
unsigned int reconnect_delay;
|
||||
unsigned int reconnect_delay_max;
|
||||
bool reconnect_exponential_backoff;
|
||||
bool threaded;
|
||||
struct _mosquitto_packet *out_packet_last;
|
||||
int inflight_messages;
|
||||
int max_inflight_messages;
|
||||
# ifdef WITH_SRV
|
||||
ares_channel achan;
|
||||
# endif
|
||||
#endif
|
||||
};
|
||||
|
||||
#endif
|
||||
53
lib/mqtt3_protocol.h
Normal file
53
lib/mqtt3_protocol.h
Normal file
@@ -0,0 +1,53 @@
|
||||
/*
|
||||
Copyright (c) 2009-2014 Roger Light <roger@atchoo.org>
|
||||
|
||||
All rights reserved. This program and the accompanying materials
|
||||
are made available under the terms of the Eclipse Public License v1.0
|
||||
and Eclipse Distribution License v1.0 which accompany this distribution.
|
||||
|
||||
The Eclipse Public License is available at
|
||||
http://www.eclipse.org/legal/epl-v10.html
|
||||
and the Eclipse Distribution License is available at
|
||||
http://www.eclipse.org/org/documents/edl-v10.php.
|
||||
|
||||
Contributors:
|
||||
Roger Light - initial implementation and documentation.
|
||||
*/
|
||||
|
||||
#ifndef _MQTT3_PROTOCOL_H_
|
||||
#define _MQTT3_PROTOCOL_H_
|
||||
|
||||
/* For version 3 of the MQTT protocol */
|
||||
|
||||
#define PROTOCOL_NAME_v31 "MQIsdp"
|
||||
#define PROTOCOL_VERSION_v31 3
|
||||
|
||||
#define PROTOCOL_NAME_v311 "MQTT"
|
||||
#define PROTOCOL_VERSION_v311 4
|
||||
|
||||
/* Message types */
|
||||
#define CONNECT 0x10
|
||||
#define CONNACK 0x20
|
||||
#define PUBLISH 0x30
|
||||
#define PUBACK 0x40
|
||||
#define PUBREC 0x50
|
||||
#define PUBREL 0x60
|
||||
#define PUBCOMP 0x70
|
||||
#define SUBSCRIBE 0x80
|
||||
#define SUBACK 0x90
|
||||
#define UNSUBSCRIBE 0xA0
|
||||
#define UNSUBACK 0xB0
|
||||
#define PINGREQ 0xC0
|
||||
#define PINGRESP 0xD0
|
||||
#define DISCONNECT 0xE0
|
||||
|
||||
#define CONNACK_ACCEPTED 0
|
||||
#define CONNACK_REFUSED_PROTOCOL_VERSION 1
|
||||
#define CONNACK_REFUSED_IDENTIFIER_REJECTED 2
|
||||
#define CONNACK_REFUSED_SERVER_UNAVAILABLE 3
|
||||
#define CONNACK_REFUSED_BAD_USERNAME_PASSWORD 4
|
||||
#define CONNACK_REFUSED_NOT_AUTHORIZED 5
|
||||
|
||||
#define MQTT_MAX_PAYLOAD 268435455
|
||||
|
||||
#endif
|
||||
1116
lib/net_mosq.c
Normal file
1116
lib/net_mosq.c
Normal file
File diff suppressed because it is too large
Load Diff
91
lib/net_mosq.h
Normal file
91
lib/net_mosq.h
Normal file
@@ -0,0 +1,91 @@
|
||||
/*
|
||||
Copyright (c) 2010-2014 Roger Light <roger@atchoo.org>
|
||||
|
||||
All rights reserved. This program and the accompanying materials
|
||||
are made available under the terms of the Eclipse Public License v1.0
|
||||
and Eclipse Distribution License v1.0 which accompany this distribution.
|
||||
|
||||
The Eclipse Public License is available at
|
||||
http://www.eclipse.org/legal/epl-v10.html
|
||||
and the Eclipse Distribution License is available at
|
||||
http://www.eclipse.org/org/documents/edl-v10.php.
|
||||
|
||||
Contributors:
|
||||
Roger Light - initial implementation and documentation.
|
||||
*/
|
||||
#ifndef _NET_MOSQ_H_
|
||||
#define _NET_MOSQ_H_
|
||||
|
||||
#ifndef WIN32
|
||||
#include <unistd.h>
|
||||
#else
|
||||
#include <winsock2.h>
|
||||
typedef int ssize_t;
|
||||
#endif
|
||||
|
||||
#include <mosquitto_internal.h>
|
||||
#include <mosquitto.h>
|
||||
|
||||
#ifdef WITH_BROKER
|
||||
struct mosquitto_db;
|
||||
#endif
|
||||
|
||||
#ifdef WIN32
|
||||
# define COMPAT_CLOSE(a) closesocket(a)
|
||||
# define COMPAT_ECONNRESET WSAECONNRESET
|
||||
# define COMPAT_EWOULDBLOCK WSAEWOULDBLOCK
|
||||
#else
|
||||
# define COMPAT_CLOSE(a) close(a)
|
||||
# define COMPAT_ECONNRESET ECONNRESET
|
||||
# define COMPAT_EWOULDBLOCK EWOULDBLOCK
|
||||
#endif
|
||||
|
||||
#ifndef WIN32
|
||||
#else
|
||||
#endif
|
||||
|
||||
/* For when not using winsock libraries. */
|
||||
#ifndef INVALID_SOCKET
|
||||
#define INVALID_SOCKET -1
|
||||
#endif
|
||||
|
||||
/* Macros for accessing the MSB and LSB of a uint16_t */
|
||||
#define MOSQ_MSB(A) (uint8_t)((A & 0xFF00) >> 8)
|
||||
#define MOSQ_LSB(A) (uint8_t)(A & 0x00FF)
|
||||
|
||||
void _mosquitto_net_init(void);
|
||||
void _mosquitto_net_cleanup(void);
|
||||
|
||||
void _mosquitto_packet_cleanup(struct _mosquitto_packet *packet);
|
||||
int _mosquitto_packet_queue(struct mosquitto *mosq, struct _mosquitto_packet *packet);
|
||||
int _mosquitto_socket_connect(struct mosquitto *mosq, const char *host, uint16_t port, const char *bind_address, bool blocking);
|
||||
int _mosquitto_socket_close(struct mosquitto *mosq);
|
||||
int _mosquitto_try_connect(const char *host, uint16_t port, int *sock, const char *bind_address, bool blocking);
|
||||
int _mosquitto_socket_nonblock(int sock);
|
||||
int _mosquitto_socketpair(int *sp1, int *sp2);
|
||||
|
||||
int _mosquitto_read_byte(struct _mosquitto_packet *packet, uint8_t *byte);
|
||||
int _mosquitto_read_bytes(struct _mosquitto_packet *packet, void *bytes, uint32_t count);
|
||||
int _mosquitto_read_string(struct _mosquitto_packet *packet, char **str);
|
||||
int _mosquitto_read_uint16(struct _mosquitto_packet *packet, uint16_t *word);
|
||||
|
||||
void _mosquitto_write_byte(struct _mosquitto_packet *packet, uint8_t byte);
|
||||
void _mosquitto_write_bytes(struct _mosquitto_packet *packet, const void *bytes, uint32_t count);
|
||||
void _mosquitto_write_string(struct _mosquitto_packet *packet, const char *str, uint16_t length);
|
||||
void _mosquitto_write_uint16(struct _mosquitto_packet *packet, uint16_t word);
|
||||
|
||||
ssize_t _mosquitto_net_read(struct mosquitto *mosq, void *buf, size_t count);
|
||||
ssize_t _mosquitto_net_write(struct mosquitto *mosq, void *buf, size_t count);
|
||||
|
||||
int _mosquitto_packet_write(struct mosquitto *mosq);
|
||||
#ifdef WITH_BROKER
|
||||
int _mosquitto_packet_read(struct mosquitto_db *db, struct mosquitto *mosq);
|
||||
#else
|
||||
int _mosquitto_packet_read(struct mosquitto *mosq);
|
||||
#endif
|
||||
|
||||
#ifdef WITH_TLS
|
||||
int _mosquitto_socket_apply_tls(struct mosquitto *mosq);
|
||||
#endif
|
||||
|
||||
#endif
|
||||
155
lib/read_handle.c
Normal file
155
lib/read_handle.c
Normal file
@@ -0,0 +1,155 @@
|
||||
/*
|
||||
Copyright (c) 2009-2014 Roger Light <roger@atchoo.org>
|
||||
|
||||
All rights reserved. This program and the accompanying materials
|
||||
are made available under the terms of the Eclipse Public License v1.0
|
||||
and Eclipse Distribution License v1.0 which accompany this distribution.
|
||||
|
||||
The Eclipse Public License is available at
|
||||
http://www.eclipse.org/legal/epl-v10.html
|
||||
and the Eclipse Distribution License is available at
|
||||
http://www.eclipse.org/org/documents/edl-v10.php.
|
||||
|
||||
Contributors:
|
||||
Roger Light - initial implementation and documentation.
|
||||
*/
|
||||
|
||||
#include <assert.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
|
||||
#include <mosquitto.h>
|
||||
#include <logging_mosq.h>
|
||||
#include <memory_mosq.h>
|
||||
#include <messages_mosq.h>
|
||||
#include <mqtt3_protocol.h>
|
||||
#include <net_mosq.h>
|
||||
#include <read_handle.h>
|
||||
#include <send_mosq.h>
|
||||
#include <time_mosq.h>
|
||||
#include <util_mosq.h>
|
||||
|
||||
int _mosquitto_packet_handle(struct mosquitto *mosq)
|
||||
{
|
||||
assert(mosq);
|
||||
|
||||
switch((mosq->in_packet.command)&0xF0){
|
||||
case PINGREQ:
|
||||
return _mosquitto_handle_pingreq(mosq);
|
||||
case PINGRESP:
|
||||
return _mosquitto_handle_pingresp(mosq);
|
||||
case PUBACK:
|
||||
return _mosquitto_handle_pubackcomp(mosq, "PUBACK");
|
||||
case PUBCOMP:
|
||||
return _mosquitto_handle_pubackcomp(mosq, "PUBCOMP");
|
||||
case PUBLISH:
|
||||
return _mosquitto_handle_publish(mosq);
|
||||
case PUBREC:
|
||||
return _mosquitto_handle_pubrec(mosq);
|
||||
case PUBREL:
|
||||
return _mosquitto_handle_pubrel(NULL, mosq);
|
||||
case CONNACK:
|
||||
return _mosquitto_handle_connack(mosq);
|
||||
case SUBACK:
|
||||
return _mosquitto_handle_suback(mosq);
|
||||
case UNSUBACK:
|
||||
return _mosquitto_handle_unsuback(mosq);
|
||||
default:
|
||||
/* If we don't recognise the command, return an error straight away. */
|
||||
_mosquitto_log_printf(mosq, MOSQ_LOG_ERR, "Error: Unrecognised command %d\n", (mosq->in_packet.command)&0xF0);
|
||||
return MOSQ_ERR_PROTOCOL;
|
||||
}
|
||||
}
|
||||
|
||||
int _mosquitto_handle_publish(struct mosquitto *mosq)
|
||||
{
|
||||
uint8_t header;
|
||||
struct mosquitto_message_all *message;
|
||||
int rc = 0;
|
||||
uint16_t mid;
|
||||
|
||||
assert(mosq);
|
||||
|
||||
message = _mosquitto_calloc(1, sizeof(struct mosquitto_message_all));
|
||||
if(!message) return MOSQ_ERR_NOMEM;
|
||||
|
||||
header = mosq->in_packet.command;
|
||||
|
||||
message->dup = (header & 0x08)>>3;
|
||||
message->msg.qos = (header & 0x06)>>1;
|
||||
message->msg.retain = (header & 0x01);
|
||||
|
||||
rc = _mosquitto_read_string(&mosq->in_packet, &message->msg.topic);
|
||||
if(rc){
|
||||
_mosquitto_message_cleanup(&message);
|
||||
return rc;
|
||||
}
|
||||
if(!strlen(message->msg.topic)){
|
||||
_mosquitto_message_cleanup(&message);
|
||||
return MOSQ_ERR_PROTOCOL;
|
||||
}
|
||||
|
||||
if(message->msg.qos > 0){
|
||||
rc = _mosquitto_read_uint16(&mosq->in_packet, &mid);
|
||||
if(rc){
|
||||
_mosquitto_message_cleanup(&message);
|
||||
return rc;
|
||||
}
|
||||
message->msg.mid = (int)mid;
|
||||
}
|
||||
|
||||
message->msg.payloadlen = mosq->in_packet.remaining_length - mosq->in_packet.pos;
|
||||
if(message->msg.payloadlen){
|
||||
message->msg.payload = _mosquitto_calloc(message->msg.payloadlen+1, sizeof(uint8_t));
|
||||
if(!message->msg.payload){
|
||||
_mosquitto_message_cleanup(&message);
|
||||
return MOSQ_ERR_NOMEM;
|
||||
}
|
||||
rc = _mosquitto_read_bytes(&mosq->in_packet, message->msg.payload, message->msg.payloadlen);
|
||||
if(rc){
|
||||
_mosquitto_message_cleanup(&message);
|
||||
return rc;
|
||||
}
|
||||
}
|
||||
_mosquitto_log_printf(mosq, MOSQ_LOG_DEBUG,
|
||||
"Client %s received PUBLISH (d%d, q%d, r%d, m%d, '%s', ... (%ld bytes))",
|
||||
mosq->id, message->dup, message->msg.qos, message->msg.retain,
|
||||
message->msg.mid, message->msg.topic,
|
||||
(long)message->msg.payloadlen);
|
||||
|
||||
message->timestamp = mosquitto_time();
|
||||
switch(message->msg.qos){
|
||||
case 0:
|
||||
pthread_mutex_lock(&mosq->callback_mutex);
|
||||
if(mosq->on_message){
|
||||
mosq->in_callback = true;
|
||||
mosq->on_message(mosq, mosq->userdata, &message->msg);
|
||||
mosq->in_callback = false;
|
||||
}
|
||||
pthread_mutex_unlock(&mosq->callback_mutex);
|
||||
_mosquitto_message_cleanup(&message);
|
||||
return MOSQ_ERR_SUCCESS;
|
||||
case 1:
|
||||
rc = _mosquitto_send_puback(mosq, message->msg.mid);
|
||||
pthread_mutex_lock(&mosq->callback_mutex);
|
||||
if(mosq->on_message){
|
||||
mosq->in_callback = true;
|
||||
mosq->on_message(mosq, mosq->userdata, &message->msg);
|
||||
mosq->in_callback = false;
|
||||
}
|
||||
pthread_mutex_unlock(&mosq->callback_mutex);
|
||||
_mosquitto_message_cleanup(&message);
|
||||
return rc;
|
||||
case 2:
|
||||
rc = _mosquitto_send_pubrec(mosq, message->msg.mid);
|
||||
pthread_mutex_lock(&mosq->in_message_mutex);
|
||||
message->state = mosq_ms_wait_for_pubrel;
|
||||
_mosquitto_message_queue(mosq, message, mosq_md_in);
|
||||
pthread_mutex_unlock(&mosq->in_message_mutex);
|
||||
return rc;
|
||||
default:
|
||||
_mosquitto_message_cleanup(&message);
|
||||
return MOSQ_ERR_PROTOCOL;
|
||||
}
|
||||
}
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user