mirror of
https://github.com/espressif/esp-protocols.git
synced 2025-12-04 16:19:20 +01:00
463 lines
15 KiB
C
463 lines
15 KiB
C
|
|
/*
|
||
|
|
* SPDX-FileCopyrightText: 2015-2025 Espressif Systems (Shanghai) CO LTD
|
||
|
|
*
|
||
|
|
* SPDX-License-Identifier: Apache-2.0
|
||
|
|
*/
|
||
|
|
#include <string.h>
|
||
|
|
#include "mdns_private.h"
|
||
|
|
#include "mdns_networking.h"
|
||
|
|
#include "mdns_pcb.h"
|
||
|
|
#include "mdns_netif.h"
|
||
|
|
#include "mdns_utils.h"
|
||
|
|
#include "mdns_send.h"
|
||
|
|
#include "mdns_mem_caps.h"
|
||
|
|
#include "esp_log.h"
|
||
|
|
#include "esp_random.h"
|
||
|
|
#include "mdns_responder.h"
|
||
|
|
|
||
|
|
#define PCB_STATE_IS_PROBING(s) (s->state > PCB_OFF && s->state < PCB_ANNOUNCE_1)
|
||
|
|
#define PCB_STATE_IS_ANNOUNCING(s) (s->state > PCB_PROBE_3 && s->state < PCB_RUNNING)
|
||
|
|
|
||
|
|
typedef enum {
|
||
|
|
PCB_OFF, PCB_DUP, PCB_INIT,
|
||
|
|
PCB_PROBE_1, PCB_PROBE_2, PCB_PROBE_3,
|
||
|
|
PCB_ANNOUNCE_1, PCB_ANNOUNCE_2, PCB_ANNOUNCE_3,
|
||
|
|
PCB_RUNNING
|
||
|
|
} mdns_pcb_state_t;
|
||
|
|
|
||
|
|
typedef struct {
|
||
|
|
mdns_pcb_state_t state;
|
||
|
|
mdns_srv_item_t **probe_services;
|
||
|
|
uint8_t probe_services_len;
|
||
|
|
uint8_t probe_ip;
|
||
|
|
uint8_t probe_running;
|
||
|
|
uint16_t failed_probes;
|
||
|
|
} mdns_pcb_t;
|
||
|
|
|
||
|
|
static const char *TAG = "mdns_pcb";
|
||
|
|
static mdns_pcb_t s_pcbs[MDNS_MAX_INTERFACES][MDNS_IP_PROTOCOL_MAX];
|
||
|
|
|
||
|
|
/**
|
||
|
|
* @brief Send announcement on particular PCB
|
||
|
|
*/
|
||
|
|
void mdns_priv_pcb_announce(mdns_if_t tcpip_if, mdns_ip_protocol_t ip_protocol, mdns_srv_item_t **services, size_t len, bool include_ip)
|
||
|
|
{
|
||
|
|
mdns_pcb_t *_pcb = &s_pcbs[tcpip_if][ip_protocol];
|
||
|
|
size_t i;
|
||
|
|
if (mdns_priv_if_ready(tcpip_if, ip_protocol)) {
|
||
|
|
if (PCB_STATE_IS_PROBING(_pcb)) {
|
||
|
|
mdns_priv_init_pcb_probe(tcpip_if, ip_protocol, services, len, include_ip);
|
||
|
|
} else if (PCB_STATE_IS_ANNOUNCING(_pcb)) {
|
||
|
|
mdns_tx_packet_t *p = mdns_priv_get_next_packet(tcpip_if, ip_protocol);
|
||
|
|
if (p) {
|
||
|
|
for (i = 0; i < len; i++) {
|
||
|
|
if (!mdns_priv_create_answer(&p->answers, MDNS_TYPE_SDPTR, services[i]->service, NULL, false, false)
|
||
|
|
|| !mdns_priv_create_answer(&p->answers, MDNS_TYPE_PTR, services[i]->service, NULL, false,
|
||
|
|
false)
|
||
|
|
|| !mdns_priv_create_answer(&p->answers, MDNS_TYPE_SRV, services[i]->service, NULL, true,
|
||
|
|
false)
|
||
|
|
|| !mdns_priv_create_answer(&p->answers, MDNS_TYPE_TXT, services[i]->service, NULL, true,
|
||
|
|
false)) {
|
||
|
|
break;
|
||
|
|
}
|
||
|
|
}
|
||
|
|
if (include_ip) {
|
||
|
|
mdns_priv_dealloc_answer(&p->additional, MDNS_TYPE_A, NULL);
|
||
|
|
mdns_priv_dealloc_answer(&p->additional, MDNS_TYPE_AAAA, NULL);
|
||
|
|
mdns_priv_append_host_list_in_services(&p->answers, services, len, true, false);
|
||
|
|
}
|
||
|
|
_pcb->state = PCB_ANNOUNCE_1;
|
||
|
|
}
|
||
|
|
} else if (_pcb->state == PCB_RUNNING) {
|
||
|
|
|
||
|
|
if (mdns_utils_str_null_or_empty(mdns_priv_get_global_hostname())) {
|
||
|
|
return;
|
||
|
|
}
|
||
|
|
|
||
|
|
_pcb->state = PCB_ANNOUNCE_1;
|
||
|
|
mdns_tx_packet_t *p = mdns_priv_create_announce_packet(tcpip_if, ip_protocol, services, len, include_ip);
|
||
|
|
if (p) {
|
||
|
|
mdns_priv_send_after(p, 0);
|
||
|
|
}
|
||
|
|
}
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
/**
|
||
|
|
* @brief Check if interface is duplicate (two interfaces on the same subnet)
|
||
|
|
*/
|
||
|
|
bool mdns_priv_pcb_check_for_duplicates(mdns_if_t tcpip_if)
|
||
|
|
{
|
||
|
|
mdns_if_t ifaces[MDNS_MAX_INTERFACES] = {tcpip_if, mdns_priv_netif_get_other_interface(tcpip_if) };
|
||
|
|
if (ifaces[1] == MDNS_MAX_INTERFACES) {
|
||
|
|
return false;
|
||
|
|
}
|
||
|
|
// check both this netif and the potential duplicate on all protocols
|
||
|
|
// if any of them is in duplicate state, return true
|
||
|
|
for (int i = 0; i < 2; i++) {
|
||
|
|
for (int proto = 0; proto < MDNS_IP_PROTOCOL_MAX; proto++) {
|
||
|
|
if (s_pcbs[ifaces[i]][(mdns_ip_protocol_t) proto].state == PCB_DUP) {
|
||
|
|
return true;
|
||
|
|
}
|
||
|
|
}
|
||
|
|
}
|
||
|
|
return false;
|
||
|
|
}
|
||
|
|
|
||
|
|
static esp_err_t deinit_pcb(mdns_if_t tcpip_if, mdns_ip_protocol_t ip_proto)
|
||
|
|
{
|
||
|
|
esp_err_t err = mdns_priv_if_deinit(tcpip_if, ip_proto);
|
||
|
|
mdns_pcb_t *pcb = &s_pcbs[tcpip_if][ip_proto];
|
||
|
|
if (pcb == NULL || err != ESP_OK) {
|
||
|
|
return err;
|
||
|
|
}
|
||
|
|
mdns_mem_free(pcb->probe_services);
|
||
|
|
pcb->state = PCB_OFF;
|
||
|
|
pcb->probe_ip = false;
|
||
|
|
pcb->probe_services = NULL;
|
||
|
|
pcb->probe_services_len = 0;
|
||
|
|
pcb->probe_running = false;
|
||
|
|
pcb->failed_probes = 0;
|
||
|
|
return ESP_OK;
|
||
|
|
}
|
||
|
|
|
||
|
|
/**
|
||
|
|
* @brief Restart the responder on particular PCB
|
||
|
|
*/
|
||
|
|
static void restart_pcb(mdns_if_t tcpip_if, mdns_ip_protocol_t ip_protocol)
|
||
|
|
{
|
||
|
|
size_t srv_count = 0;
|
||
|
|
mdns_srv_item_t *a = mdns_priv_get_services();
|
||
|
|
while (a) {
|
||
|
|
srv_count++;
|
||
|
|
a = a->next;
|
||
|
|
}
|
||
|
|
if (srv_count == 0) {
|
||
|
|
// proble only IP
|
||
|
|
mdns_priv_init_pcb_probe(tcpip_if, ip_protocol, NULL, 0, true);
|
||
|
|
return;
|
||
|
|
}
|
||
|
|
mdns_srv_item_t *services[srv_count];
|
||
|
|
size_t i = 0;
|
||
|
|
a = mdns_priv_get_services();
|
||
|
|
while (a) {
|
||
|
|
services[i++] = a;
|
||
|
|
a = a->next;
|
||
|
|
}
|
||
|
|
mdns_priv_init_pcb_probe(tcpip_if, ip_protocol, services, srv_count, true);
|
||
|
|
}
|
||
|
|
|
||
|
|
/**
|
||
|
|
* @brief Disable mDNS interface
|
||
|
|
*/
|
||
|
|
void mdns_priv_pcb_disable(mdns_if_t tcpip_if, mdns_ip_protocol_t ip_protocol)
|
||
|
|
{
|
||
|
|
mdns_priv_netif_disable(tcpip_if);
|
||
|
|
|
||
|
|
if (mdns_priv_if_ready(tcpip_if, ip_protocol)) {
|
||
|
|
mdns_priv_clear_tx_queue_if(tcpip_if, ip_protocol);
|
||
|
|
deinit_pcb(tcpip_if, ip_protocol);
|
||
|
|
mdns_if_t other_if = mdns_priv_netif_get_other_interface(tcpip_if);
|
||
|
|
if (other_if != MDNS_MAX_INTERFACES && s_pcbs[other_if][ip_protocol].state == PCB_DUP) {
|
||
|
|
s_pcbs[other_if][ip_protocol].state = PCB_OFF;
|
||
|
|
mdns_priv_pcb_enable(other_if, ip_protocol);
|
||
|
|
}
|
||
|
|
}
|
||
|
|
s_pcbs[tcpip_if][ip_protocol].state = PCB_OFF;
|
||
|
|
}
|
||
|
|
|
||
|
|
/**
|
||
|
|
* @brief Enable mDNS interface
|
||
|
|
*/
|
||
|
|
void mdns_priv_pcb_enable(mdns_if_t tcpip_if, mdns_ip_protocol_t ip_protocol)
|
||
|
|
{
|
||
|
|
if (!mdns_priv_if_ready(tcpip_if, ip_protocol)) {
|
||
|
|
if (mdns_priv_if_init(tcpip_if, ip_protocol)) {
|
||
|
|
s_pcbs[tcpip_if][ip_protocol].failed_probes = 0;
|
||
|
|
return;
|
||
|
|
}
|
||
|
|
}
|
||
|
|
restart_pcb(tcpip_if, ip_protocol);
|
||
|
|
}
|
||
|
|
|
||
|
|
/**
|
||
|
|
* @brief Set interface as duplicate if another is found on the same subnet
|
||
|
|
*/
|
||
|
|
void mdns_priv_pcb_set_duplicate(mdns_if_t tcpip_if)
|
||
|
|
{
|
||
|
|
uint8_t i;
|
||
|
|
mdns_if_t other_if = mdns_priv_netif_get_other_interface(tcpip_if);
|
||
|
|
if (other_if == MDNS_MAX_INTERFACES) {
|
||
|
|
return; // no other interface found
|
||
|
|
}
|
||
|
|
for (i = 0; i < MDNS_IP_PROTOCOL_MAX; i++) {
|
||
|
|
if (mdns_priv_if_ready(other_if, i)) {
|
||
|
|
//stop this interface and mark as dup
|
||
|
|
if (mdns_priv_if_ready(tcpip_if, i)) {
|
||
|
|
mdns_priv_clear_tx_queue_if(tcpip_if, i);
|
||
|
|
deinit_pcb(tcpip_if, i);
|
||
|
|
}
|
||
|
|
s_pcbs[tcpip_if][i].state = PCB_DUP;
|
||
|
|
mdns_priv_pcb_announce(other_if, i, NULL, 0, true);
|
||
|
|
}
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
bool mdns_priv_pcb_is_off(mdns_if_t tcpip_if, mdns_ip_protocol_t ip_protocol)
|
||
|
|
{
|
||
|
|
return s_pcbs[tcpip_if][ip_protocol].state == PCB_OFF;
|
||
|
|
}
|
||
|
|
|
||
|
|
void mdns_priv_pcb_schedule_tx_packet(mdns_tx_packet_t *p)
|
||
|
|
{
|
||
|
|
mdns_pcb_t *pcb = &s_pcbs[p->tcpip_if][p->ip_protocol];
|
||
|
|
mdns_out_question_t *q = NULL;
|
||
|
|
mdns_tx_packet_t *a = NULL;
|
||
|
|
uint32_t send_after = 1000;
|
||
|
|
switch (pcb->state) {
|
||
|
|
case PCB_PROBE_1:
|
||
|
|
q = p->questions;
|
||
|
|
while (q) {
|
||
|
|
q->unicast = false;
|
||
|
|
q = q->next;
|
||
|
|
}
|
||
|
|
//fallthrough
|
||
|
|
case PCB_PROBE_2:
|
||
|
|
mdns_priv_send_after(p, 250);
|
||
|
|
pcb->state = (mdns_pcb_state_t)((uint8_t)(pcb->state) + 1);
|
||
|
|
break;
|
||
|
|
case PCB_PROBE_3:
|
||
|
|
a = mdns_priv_create_announce_from_probe(p);
|
||
|
|
if (!a) {
|
||
|
|
mdns_priv_send_after(p, 250);
|
||
|
|
break;
|
||
|
|
}
|
||
|
|
pcb->probe_running = false;
|
||
|
|
pcb->probe_ip = false;
|
||
|
|
pcb->probe_services_len = 0;
|
||
|
|
pcb->failed_probes = 0;
|
||
|
|
mdns_mem_free(pcb->probe_services);
|
||
|
|
pcb->probe_services = NULL;
|
||
|
|
mdns_priv_free_tx_packet(p);
|
||
|
|
p = a;
|
||
|
|
send_after = 250;
|
||
|
|
//fallthrough
|
||
|
|
case PCB_ANNOUNCE_1:
|
||
|
|
//fallthrough
|
||
|
|
case PCB_ANNOUNCE_2:
|
||
|
|
mdns_priv_send_after(p, send_after);
|
||
|
|
pcb->state = (mdns_pcb_state_t)((uint8_t)(pcb->state) + 1);
|
||
|
|
break;
|
||
|
|
case PCB_ANNOUNCE_3:
|
||
|
|
pcb->state = PCB_RUNNING;
|
||
|
|
mdns_priv_free_tx_packet(p);
|
||
|
|
break;
|
||
|
|
default:
|
||
|
|
mdns_priv_free_tx_packet(p);
|
||
|
|
break;
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
void mdns_priv_pcb_check_probing_services(mdns_if_t tcpip_if, mdns_ip_protocol_t ip_protocol, mdns_service_t *service, bool removed_answers, bool *should_remove_questions)
|
||
|
|
{
|
||
|
|
mdns_pcb_t *_pcb = &s_pcbs[tcpip_if][ip_protocol];
|
||
|
|
|
||
|
|
if (PCB_STATE_IS_PROBING(_pcb)) {
|
||
|
|
uint8_t i;
|
||
|
|
//check if we are probing this service
|
||
|
|
for (i = 0; i < _pcb->probe_services_len; i++) {
|
||
|
|
mdns_srv_item_t *s = _pcb->probe_services[i];
|
||
|
|
if (s->service == service) {
|
||
|
|
break;
|
||
|
|
}
|
||
|
|
}
|
||
|
|
if (i < _pcb->probe_services_len) {
|
||
|
|
if (_pcb->probe_services_len > 1) {
|
||
|
|
uint8_t n;
|
||
|
|
for (n = (i + 1); n < _pcb->probe_services_len; n++) {
|
||
|
|
_pcb->probe_services[n - 1] = _pcb->probe_services[n];
|
||
|
|
}
|
||
|
|
_pcb->probe_services_len--;
|
||
|
|
} else {
|
||
|
|
_pcb->probe_services_len = 0;
|
||
|
|
mdns_mem_free(_pcb->probe_services);
|
||
|
|
_pcb->probe_services = NULL;
|
||
|
|
if (!_pcb->probe_ip) {
|
||
|
|
_pcb->probe_running = false;
|
||
|
|
_pcb->state = PCB_RUNNING;
|
||
|
|
}
|
||
|
|
}
|
||
|
|
*should_remove_questions = true;
|
||
|
|
return;
|
||
|
|
}
|
||
|
|
} else if (PCB_STATE_IS_ANNOUNCING(_pcb)) {
|
||
|
|
//if answers were cleared, set to running
|
||
|
|
if (removed_answers) {
|
||
|
|
_pcb->state = PCB_RUNNING;
|
||
|
|
}
|
||
|
|
}
|
||
|
|
*should_remove_questions = false;
|
||
|
|
}
|
||
|
|
|
||
|
|
void mdns_priv_pcb_deinit(void)
|
||
|
|
{
|
||
|
|
for (int i = 0; i < MDNS_MAX_INTERFACES; i++) {
|
||
|
|
for (int j = 0; j < MDNS_IP_PROTOCOL_MAX; j++) {
|
||
|
|
deinit_pcb(i, j);
|
||
|
|
}
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
bool mdsn_priv_pcb_is_inited(mdns_if_t tcpip_if, mdns_ip_protocol_t ip_protocol)
|
||
|
|
{
|
||
|
|
return mdns_priv_if_ready(tcpip_if, ip_protocol) && s_pcbs[tcpip_if][ip_protocol].state > PCB_INIT;
|
||
|
|
}
|
||
|
|
|
||
|
|
bool mdns_priv_pcb_is_duplicate(mdns_if_t tcpip_if, mdns_ip_protocol_t ip_protocol)
|
||
|
|
{
|
||
|
|
return s_pcbs[tcpip_if][ip_protocol].state == PCB_DUP;
|
||
|
|
}
|
||
|
|
|
||
|
|
bool mdns_priv_pcb_is_probing(mdns_rx_packet_t *packet)
|
||
|
|
{
|
||
|
|
return s_pcbs[packet->tcpip_if][packet->ip_protocol].probe_running;
|
||
|
|
}
|
||
|
|
|
||
|
|
bool mdns_priv_pcb_is_after_probing(mdns_rx_packet_t *packet)
|
||
|
|
{
|
||
|
|
return s_pcbs[packet->tcpip_if][packet->ip_protocol].state > PCB_PROBE_3;
|
||
|
|
}
|
||
|
|
|
||
|
|
void mdns_priv_pcb_set_probe_failed(mdns_rx_packet_t *packet)
|
||
|
|
{
|
||
|
|
s_pcbs[packet->tcpip_if][packet->ip_protocol].failed_probes++;
|
||
|
|
}
|
||
|
|
|
||
|
|
/**
|
||
|
|
* @brief Send probe for additional services on particular PCB
|
||
|
|
*/
|
||
|
|
static void init_probe_new_service(mdns_if_t tcpip_if, mdns_ip_protocol_t ip_protocol, mdns_srv_item_t **services, size_t len, bool probe_ip)
|
||
|
|
{
|
||
|
|
mdns_pcb_t *pcb = &s_pcbs[tcpip_if][ip_protocol];
|
||
|
|
size_t services_final_len = len;
|
||
|
|
|
||
|
|
if (PCB_STATE_IS_PROBING(pcb)) {
|
||
|
|
services_final_len += pcb->probe_services_len;
|
||
|
|
}
|
||
|
|
mdns_srv_item_t **s = NULL;
|
||
|
|
if (services_final_len) {
|
||
|
|
s = (mdns_srv_item_t **)mdns_mem_malloc(sizeof(mdns_srv_item_t *) * services_final_len);
|
||
|
|
if (!s) {
|
||
|
|
HOOK_MALLOC_FAILED;
|
||
|
|
return;
|
||
|
|
}
|
||
|
|
|
||
|
|
size_t i;
|
||
|
|
for (i = 0; i < len; i++) {
|
||
|
|
s[i] = services[i];
|
||
|
|
}
|
||
|
|
if (pcb->probe_services) {
|
||
|
|
for (i = 0; i < pcb->probe_services_len; i++) {
|
||
|
|
s[len + i] = pcb->probe_services[i];
|
||
|
|
}
|
||
|
|
mdns_mem_free(pcb->probe_services);
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
probe_ip = pcb->probe_ip || probe_ip;
|
||
|
|
|
||
|
|
pcb->probe_ip = false;
|
||
|
|
pcb->probe_services = NULL;
|
||
|
|
pcb->probe_services_len = 0;
|
||
|
|
pcb->probe_running = false;
|
||
|
|
|
||
|
|
mdns_tx_packet_t *packet = mdns_priv_create_probe_packet(tcpip_if, ip_protocol, s, services_final_len, true,
|
||
|
|
probe_ip);
|
||
|
|
if (!packet) {
|
||
|
|
mdns_mem_free(s);
|
||
|
|
return;
|
||
|
|
}
|
||
|
|
|
||
|
|
pcb->probe_ip = probe_ip;
|
||
|
|
pcb->probe_services = s;
|
||
|
|
pcb->probe_services_len = services_final_len;
|
||
|
|
pcb->probe_running = true;
|
||
|
|
mdns_priv_send_after(packet, ((pcb->failed_probes > 5) ? 1000 : 120) + (esp_random() & 0x7F));
|
||
|
|
pcb->state = PCB_PROBE_1;
|
||
|
|
}
|
||
|
|
|
||
|
|
void mdns_priv_init_pcb_probe(mdns_if_t tcpip_if, mdns_ip_protocol_t ip_protocol, mdns_srv_item_t **services, size_t len, bool probe_ip)
|
||
|
|
{
|
||
|
|
mdns_pcb_t *pcb = &s_pcbs[tcpip_if][ip_protocol];
|
||
|
|
|
||
|
|
mdns_priv_clear_tx_queue_if(tcpip_if, ip_protocol);
|
||
|
|
|
||
|
|
if (mdns_utils_str_null_or_empty(mdns_priv_get_global_hostname())) {
|
||
|
|
pcb->state = PCB_RUNNING;
|
||
|
|
return;
|
||
|
|
}
|
||
|
|
|
||
|
|
if (PCB_STATE_IS_PROBING(pcb)) {
|
||
|
|
// Looking for already probing services to resolve duplications
|
||
|
|
mdns_srv_item_t *new_probe_services[len];
|
||
|
|
int new_probe_service_len = 0;
|
||
|
|
bool found;
|
||
|
|
for (size_t j = 0; j < len; ++j) {
|
||
|
|
found = false;
|
||
|
|
for (int i = 0; i < pcb->probe_services_len; ++i) {
|
||
|
|
if (pcb->probe_services[i] == services[j]) {
|
||
|
|
found = true;
|
||
|
|
break;
|
||
|
|
}
|
||
|
|
}
|
||
|
|
if (!found) {
|
||
|
|
new_probe_services[new_probe_service_len++] = services[j];
|
||
|
|
}
|
||
|
|
}
|
||
|
|
// init probing for newly added services
|
||
|
|
init_probe_new_service(tcpip_if, ip_protocol,
|
||
|
|
new_probe_service_len ? new_probe_services : NULL, new_probe_service_len, probe_ip);
|
||
|
|
} else {
|
||
|
|
// not probing, so init for all services
|
||
|
|
init_probe_new_service(tcpip_if, ip_protocol, services, len, probe_ip);
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
/**
|
||
|
|
* @brief Send by for particular services
|
||
|
|
*/
|
||
|
|
void mdns_priv_pcb_send_bye_service(mdns_srv_item_t **services, size_t len, bool include_ip)
|
||
|
|
{
|
||
|
|
uint8_t i, j;
|
||
|
|
if (mdns_utils_str_null_or_empty(mdns_priv_get_global_hostname())) {
|
||
|
|
return;
|
||
|
|
}
|
||
|
|
|
||
|
|
for (i = 0; i < MDNS_MAX_INTERFACES; i++) {
|
||
|
|
for (j = 0; j < MDNS_IP_PROTOCOL_MAX; j++) {
|
||
|
|
if (mdns_priv_if_ready(i, j) && s_pcbs[i][j].state == PCB_RUNNING) {
|
||
|
|
mdns_priv_send_bye((mdns_if_t) i, (mdns_ip_protocol_t) j, services, len, include_ip);
|
||
|
|
}
|
||
|
|
}
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
void mdns_priv_probe_all_pcbs(mdns_srv_item_t **services, size_t len, bool probe_ip, bool clear_old_probe)
|
||
|
|
{
|
||
|
|
uint8_t i, j;
|
||
|
|
for (i = 0; i < MDNS_MAX_INTERFACES; i++) {
|
||
|
|
for (j = 0; j < MDNS_IP_PROTOCOL_MAX; j++) {
|
||
|
|
if (mdns_priv_if_ready(i, j)) {
|
||
|
|
mdns_pcb_t *_pcb = &s_pcbs[i][j];
|
||
|
|
if (clear_old_probe) {
|
||
|
|
mdns_mem_free(_pcb->probe_services);
|
||
|
|
_pcb->probe_services = NULL;
|
||
|
|
_pcb->probe_services_len = 0;
|
||
|
|
_pcb->probe_running = false;
|
||
|
|
}
|
||
|
|
mdns_priv_init_pcb_probe((mdns_if_t) i, (mdns_ip_protocol_t) j, services, len, probe_ip);
|
||
|
|
}
|
||
|
|
}
|
||
|
|
}
|
||
|
|
}
|