This is an automated email from the ASF dual-hosted git repository.

xiaoxiang pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/nuttx-apps.git

commit 30b1c024a1d1c59f4b7108643bead85616b4334a
Author: Tim Hardisty <56726697+tim...@users.noreply.github.com>
AuthorDate: Wed May 14 15:27:30 2025 +0100

    apps/netutils: add mdns library support
    
    This commit allows an external mDNS library to be included in NuttX.
    
    It originates from here: <https://github.com/mjansson/mdns>
    
    It is declared as being in the Public Domain as per <http://unlicense.org>
    
    Signed-off-by: Tim Hardisty <t...@jti.uk.com>
---
 include/netutils/mdnsd.h           |  58 ++++++++++++
 netutils/mdns/Kconfig              |  81 +++++++++++++++++
 netutils/mdns/Make.defs            |  25 +++++
 netutils/mdns/Makefile             | 106 +++++++++++++++++++++
 netutils/mdns/mdnsd.c              | 182 +++++++++++++++++++++++++++++++++++++
 netutils/mdns/verbose_option.patch |  16 ++++
 6 files changed, 468 insertions(+)

diff --git a/include/netutils/mdnsd.h b/include/netutils/mdnsd.h
new file mode 100644
index 000000000..1900fb9db
--- /dev/null
+++ b/include/netutils/mdnsd.h
@@ -0,0 +1,58 @@
+/****************************************************************************
+ * apps/netutils/mdnsd.h
+ *
+ * SPDX-License-Identifier: Apache-2.0
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.  The
+ * ASF licenses this file to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance with the
+ * License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.  See the
+ * License for the specific language governing permissions and limitations
+ * under the License.
+ *
+ ****************************************************************************/
+
+#ifndef __APPS_INCLUDE_NETUTILS_MDNSD_H
+#define __APPS_INCLUDE_NETUTILS_MDNSD_H
+
+/****************************************************************************
+ * Included Files
+ ****************************************************************************/
+
+/****************************************************************************
+ * Pre-processor Definitions
+ ****************************************************************************/
+
+/****************************************************************************
+ * Public Types
+ ****************************************************************************/
+
+/****************************************************************************
+ * Public Function Prototypes
+ ****************************************************************************/
+
+#ifdef __cplusplus
+#define EXTERN extern "C"
+extern "C"
+{
+#else
+#define EXTERN extern
+#endif
+
+int mdnsd_start(FAR char *service_name, FAR char *service_port);
+int mdnsd_stop(void);
+
+#undef EXTERN
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* __APPS_INCLUDE_NETUTILS_MDNSD_H */
diff --git a/netutils/mdns/Kconfig b/netutils/mdns/Kconfig
new file mode 100644
index 000000000..bd2003bdb
--- /dev/null
+++ b/netutils/mdns/Kconfig
@@ -0,0 +1,81 @@
+config LIB_MDNS
+       bool "MDNS library"
+       default n
+       ---help---
+               Enable the mDNS library. This allows calls to the library to be 
made.
+               
+               This external library is "unlicensed" using the methodology from
+               http://unlicense.org
+               
+               You should be sure that this license is acceptable for your 
usage.
+
+               By default, the "built-in" demo is added as an application that 
can
+               be run from nsh <mdns>.
+
+               This is also needed for the optional daemon that allows the demo
+               app's mDNS functionality to be started and stopped from user
+               applications. There is an associated example app
+               (CONFIG_EXAMPLES_MDNSD) to allow the daemon to be tried from 
nsh.
+
+               Ultimately, this should be used simply as a library, and 
neither the
+               demo app nor the daemon utilised. If just built as a library,the
+               relevant header file <mdns.h> is copied to the usual netutils
+               include location and can be utilised be including it:
+
+               #include <netutils/mdns.h>
+
+if LIB_MDNS
+
+config NETUTILS_MDNS
+       tristate "Enable mdns built-in demo app"
+       default n
+       ---help---
+               Enable the author's original built-in MDNS demo app. This 
allows the
+               functionality of the library to be demonstrated. Information on 
using
+               it is available from the original git repo for this external 
library:
+
+               https://github.com/mjansson/mdns
+
+if NETUTILS_MDNS
+
+config NETUTILS_MDNS_PROGNAME
+       string "mDNS program name"
+       default "mdns"
+       ---help---
+               This is the name of the program that will be used when the NSH 
ELF
+               program is installed.
+
+config NETUTILS_MDNS_PRIORITY
+       int "mDNS task priority"
+       default 100
+
+config NETUTILS_MDNS_STACKSIZE
+       int "mDNS stack size"
+       default DEFAULT_TASK_STACKSIZE
+       ---help---
+               The default (4KiB) is adequate for simple networks but this will
+               most likely need to be increased if there are many network 
devices
+               attached that could send queries.
+
+config NETUTILS_MDNS_VERBOSE
+       bool "Enable verbose printf output from built-in mdns demo"
+       default y
+endif
+
+config NETUTILS_MDNS_DAEMON
+       tristate "Wrap mdns demo app as a daemon, which can be started/stopped"
+       default n
+       depends on NETUTILS_MDNS
+       ---help---
+               This option wraps the mdns demo app as a daemon, so requires
+               CONFIG_NETUTILS_MDNS to be selected.
+
+               There is also an example app (CONFIG_EXAMPLES_MDNSD) to allow 
the
+               mdns daemon to be started/stopped via the NuttX shell.
+
+config NETUTILS_MDNS_DAEMON_STOP_SIGNAL
+       int "Signal used to stop the MDNSD daemon"
+       default 22
+       depends on NETUTILS_MDNS_DAEMON
+
+endif #NETUTILS_MDNS
diff --git a/netutils/mdns/Make.defs b/netutils/mdns/Make.defs
new file mode 100644
index 000000000..9bc358982
--- /dev/null
+++ b/netutils/mdns/Make.defs
@@ -0,0 +1,25 @@
+############################################################################
+# apps/netutils/mdns/Make.defs
+#
+# SPDX-License-Identifier: Apache-2.0
+#
+# Licensed to the Apache Software Foundation (ASF) under one or more
+# contributor license agreements.  See the NOTICE file distributed with
+# this work for additional information regarding copyright ownership.  The
+# ASF licenses this file to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance with the
+# License.  You may obtain a copy of the License at
+#
+#   http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.  See the
+# License for the specific language governing permissions and limitations
+# under the License.
+#
+############################################################################
+
+ifneq ($(CONFIG_LIB_MDNS),)
+CONFIGURED_APPS += $(APPDIR)/netutils/mdns
+endif
diff --git a/netutils/mdns/Makefile b/netutils/mdns/Makefile
new file mode 100644
index 000000000..2a69531a9
--- /dev/null
+++ b/netutils/mdns/Makefile
@@ -0,0 +1,106 @@
+############################################################################
+# netutils/mdns/Makefile
+#
+# SPDX-License-Identifier: Apache-2.0
+#
+# Licensed to the Apache Software Foundation (ASF) under one or more
+# contributor license agreements.  See the NOTICE file distributed with
+# this work for additional information regarding copyright ownership.  The
+# ASF licenses this file to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance with the
+# License.  You may obtain a copy of the License at
+#
+#   http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.  See the
+# License for the specific language governing permissions and limitations
+# under the License.
+#
+############################################################################
+
+include $(APPDIR)/Make.defs
+
+# mDNS application
+
+############################################################################
+# Flags
+############################################################################
+
+MDNS_URL ?= "https://github.com/mjansson/mdns/archive";
+
+MDNS_VERSION = main
+MDNS_ZIP = $(MDNS_VERSION).zip
+
+MDNS_UNPACKNAME = mdns
+UNPACK ?= unzip -q -o
+
+VPATH += $(MDNS_UNPACKNAME)
+VPATH += $(MDNS_UNPACKNAME)$(DELIM)posix
+DEPPATH += --dep-path $(MDNS_UNPACKNAME)
+DEPPATH += --dep-path $(MDNS_UNPACKNAME)$(DELIM)posix
+
+CFLAGS += -Wno-strict-prototypes -Wno-undef -Wno-format
+
+APPS_INCDIR = $(APPDIR)$(DELIM)include$(DELIM)netutils
+
+############################################################################
+# Targets
+############################################################################
+
+$(MDNS_ZIP):
+       @echo "Downloading: $(MDNS_URL)/$(MDNS_ZIP)"
+       $(Q) curl -O -L $(MDNS_URL)/$(MDNS_ZIP)
+
+$(MDNS_UNPACKNAME): $(MDNS_ZIP)
+       @echo "Unpacking: $(MDNS_ZIP) -> $(MDNS_UNPACKNAME)"
+       $(Q) $(UNPACK) $(MDNS_ZIP)
+       $(Q) mv mdns-$(MDNS_VERSION) $(MDNS_UNPACKNAME)
+       $(Q) cp $(MDNS_UNPACKNAME)$(DELIM)mdns.h $(APPS_INCDIR)
+       $(Q) patch -p0 < verbose_option.patch # Update to enable non-verbose 
mode
+       $(Q) touch $(MDNS_UNPACKNAME)
+
+clean::
+       $(call DELFILE, $(OBJS))
+
+# Download and unpack tarball if no git repo found
+
+ifeq ($(wildcard $(MDNS_UNPACKNAME)/.git),)
+context:: $(MDNS_UNPACKNAME)
+
+distclean::
+       $(call DELFILE, $(OBJS))
+       $(call DELDIR, $(MDNS_UNPACKNAME))
+       $(call DELFILE, $(APPS_INCDIR)$(DELIM)mdns.h)
+       $(call DELFILE, $(MDNS_ZIP))
+endif
+
+############################################################################
+# Applications Configuration
+############################################################################
+
+include $(APPDIR)/Make.defs
+
+ifneq ($(CONFIG_NETUTILS_MDNS),)
+PROGNAME  = $(CONFIG_NETUTILS_MDNS_PROGNAME)
+PRIORITY  = $(CONFIG_NETUTILS_MDNS_PRIORITY)
+STACKSIZE = $(CONFIG_NETUTILS_MDNS_STACKSIZE)
+MODULE    = $(CONFIG_NETUTILS_MDNS)
+
+MAINSRC = mdns/mdns.c
+else
+CSRCS += mdns/mdns.c
+endif
+
+ifneq ($(CONFIG_NETUTILS_MDNS_DAEMON),)
+CSRCS += mdnsd.c
+endif
+
+# This is an external library so we accept NuttX style violations
+
+CFLAGS += -Wno-undef -Wno-strict-prototypes -Wno-unused-variable \
+          -Wno-pointer-sign -Wno-unused-but-set-variable -Wno-shadow \
+                 -Wno-format
+
+include $(APPDIR)/Application.mk
\ No newline at end of file
diff --git a/netutils/mdns/mdnsd.c b/netutils/mdns/mdnsd.c
new file mode 100644
index 000000000..1f648950b
--- /dev/null
+++ b/netutils/mdns/mdnsd.c
@@ -0,0 +1,182 @@
+/****************************************************************************
+ * apps/netutils/mdns/mdnsd.c
+ *
+ * SPDX-License-Identifier: Apache-2.0
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.  The
+ * ASF licenses this file to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance with the
+ * License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.  See the
+ * License for the specific language governing permissions and limitations
+ * under the License.
+ *
+ ****************************************************************************/
+
+/****************************************************************************
+ * Included Files
+ ****************************************************************************/
+
+#include <nuttx/config.h>
+
+#include <stdint.h>
+#include <stdlib.h>
+#include <string.h>
+#include <syslog.h>
+#include <limits.h>
+#include <semaphore.h>
+#include <debug.h>                 /* For nerr, info */
+
+#include "netutils/netlib.h"
+#include "netutils/mdnsd.h"
+
+#include <spawn.h>
+
+/****************************************************************************
+ * Preprocessor Definitions
+ ****************************************************************************/
+
+/****************************************************************************
+ * Private Types
+ ****************************************************************************/
+
+/* This enumeration describes the state of the MDNSD daemon */
+
+enum mdnsd_daemon_e
+{
+  MDNSD_NOT_RUNNING = 0,
+  MDNSD_STARTING,
+  MDNSD_RUNNING,
+  MDNSD_STOP_REQUESTED,
+};
+
+struct mdnsd_config_s
+{
+  pid_t               pid;   /* Task ID of the spawned MDNSD daemon         */
+  enum mdnsd_daemon_e state; /* State of the daemon                         */
+  sem_t               lock;  /* Used to protect the whole structure         */
+};
+
+/****************************************************************************
+ * Private Function Prototypes
+ ****************************************************************************/
+
+/****************************************************************************
+ * Private Data
+ ****************************************************************************/
+
+struct mdnsd_config_s g_mdnsd_config =
+{
+  -1,
+  MDNSD_NOT_RUNNING,
+  SEM_INITIALIZER(1),
+};
+
+/****************************************************************************
+ * Public Data
+ ****************************************************************************/
+
+/****************************************************************************
+ * Private Functions
+ ****************************************************************************/
+
+/****************************************************************************
+ * Public Functions
+ ****************************************************************************/
+
+int mdnsd_stop(void)
+{
+  int ret;
+
+  sem_wait(&g_mdnsd_config.lock);
+  if (g_mdnsd_config.state == MDNSD_RUNNING)
+    {
+      g_mdnsd_config.state = MDNSD_STOP_REQUESTED;
+      do
+        {
+          ret = (kill(g_mdnsd_config.pid,
+                      CONFIG_NETUTILS_MDNS_DAEMON_STOP_SIGNAL));
+          if (ret < 0)
+            {
+              nerr("ERROR: kill pid %d failed: %d\n",
+                    g_mdnsd_config.pid, errno);
+              break;
+            }
+        }
+      while (g_mdnsd_config.state == MDNSD_STOP_REQUESTED);
+    }
+
+  g_mdnsd_config.state = MDNSD_NOT_RUNNING;
+  sem_post(&g_mdnsd_config.lock);
+  return OK;
+}
+
+int mdnsd_start(FAR char *service_name, FAR char *service_port)
+{
+  int ret;
+  char hostname_buffer[HOST_NAME_MAX];
+  const char *hostname = "nuttx";
+  FAR char *argv[7];
+
+  /* Are we in a non-running state? */
+
+  sem_wait(&g_mdnsd_config.lock);
+  if (g_mdnsd_config.state == MDNSD_NOT_RUNNING)
+    {
+      g_mdnsd_config.state = MDNSD_STARTING;
+
+      /* Configure our mDNS service */
+
+      /* The mdns library function will check the hostname too, but this
+       * ensures the default is our, not the library author's, choice.
+       */
+
+      if (gethostname(hostname_buffer, HOST_NAME_MAX) == 0)
+        {
+          if (strlen(hostname_buffer) != 0)
+            {
+              hostname = hostname_buffer;
+            }
+        }
+
+      argv[0] = "--service";
+      argv[1] = service_name;
+      argv[2] = "--hostname";
+      argv[3] = (char *)hostname;
+      argv[4] = "--port";
+      argv[5] = service_port;
+      argv[6] = NULL;
+
+      /* Spawn mdns app */
+
+      ret = posix_spawn(&g_mdnsd_config.pid, /* Returned Task ID            */
+                        "mdns",              /* Task Path                   */
+                        NULL,                /* File actions                */
+                        NULL,                /* Attributes                  */
+                        argv,                /* Arguments                   */
+                        NULL);               /* No                          */
+
+      if (ret < 0)
+        {
+          int errval = errno;
+          syslog(LOG_ERR, "Failed to spawn mdns daemon\n");
+          g_mdnsd_config.state = MDNSD_NOT_RUNNING;
+          return -errval;
+        }
+
+      ninfo("Started\n");
+
+      g_mdnsd_config.state = MDNSD_RUNNING;
+    }
+
+  sem_post(&g_mdnsd_config.lock);
+  return OK;
+}
+
diff --git a/netutils/mdns/verbose_option.patch 
b/netutils/mdns/verbose_option.patch
new file mode 100644
index 000000000..63e09fffd
--- /dev/null
+++ b/netutils/mdns/verbose_option.patch
@@ -0,0 +1,16 @@
+--- mdns/mdns.c
++++ mdns/mdns/mdns.c
+@@ -22,7 +22,9 @@
+ // Alias some things to simulate recieving data to fuzz library
+ #if defined(MDNS_FUZZING)
+ #define recvfrom(sock, buffer, capacity, flags, src_addr, addrlen) 
((mdns_ssize_t)capacity)
+-#define printf
++#endif
++#if defined(MDNS_FUZZING) || !defined(CONFIG_NETUTILS_MDNS_VERBOSE)
++#define printf(...)
+ #endif
+ 
+ #include "mdns.h"
+-- 
+2.34.1
+

Reply via email to