Почему сообщение прибыла функция обратного вызова дважды?Linux

Ответить
Anonymous
 Почему сообщение прибыла функция обратного вызова дважды?

Сообщение Anonymous »

Проблема
Когда я разрабатывал клиент MQTT, используя библиотеку Paho MQTT C, почему сообщение приходит с использованием обратного вызова с использованием MQTTASYNC_SETCALLBACKS дважды? Ubuntu и запуск его на платформе Arm Linux. Тем не менее, я обнаружил, что клиентская программа дважды запускает функцию обратного вызова из -за одного сообщения , поэтому я должен очистить сообщение и The TeapName во время второго триггера обратного вызова, в противном случае произойдет ошибка сегментации . /> вот моя программа C. < /h2>

Код: Выделить всё

#include "MQTTAsync.h"
#include "string.h"
#include "stdio.h"
#include 

#define SERVER_ADDRESS  "192.168.10.100"
#define CLIENT_ID       "MQTT_ZYX"
#define USER_NAME       "MQTT_test"
#define PASSWORD        "123456"

//连接断开回调函数
void cntlost(void* context, char* cause)
{
printf("connect lost\r\n");
printf("cause : %s", cause);
}

//接收到消息的回调函数
int messarri(void* context, char* topicName, int topicLen, MQTTAsync_message* message)
{
if(topicName!=NULL && (message->payload)!=NULL && message->payloadlen>0) {
printf("\r\nmessage arrive\r\n");
printf("topic is : %s\r\n", topicName);
printf("payload_len = %d\r\n", message->payloadlen);
printf("receive message : %.*s\r\n", message->payloadlen, message->payload);

message->payloadlen=0;
} else {
MQTTAsync_freeMessage(&message);
MQTTAsync_free(topicName);
}

return 0;
}

//发送完成回调函数
void delcomp(void* context, MQTTAsync_token token)
{
printf("delivery complete\r\n");
}

//连接成功回调函数
void on_connect(void* context, MQTTAsync_successData* response)
{
printf("connect success\r\n");
}

//连接失败回调函数
void on_connectFail(void* context,  MQTTAsync_failureData* response)
{
printf("connect fail: %d\r\n", response->code);
}

//发布成功回调函数
void on_send(void* context, MQTTAsync_successData* response)
{
printf("send %s success\r\n", (char *)context);
}

//发布失败回调函数
void on_notsend(void* context,  MQTTAsync_failureData* response)
{
printf("send %s failure: %d\r\n", (char *)context, response->code);
}

//订阅成功回调函数
void on_subscribe(void* context, MQTTAsync_successData* response)
{
printf("subscribe %s success\r\n", (char *)context);
}

//订阅失败回调函数
void on_dissubscribe(void* context,  MQTTAsync_failureData* response)
{
printf("subscribe %s failure: %d\r\n", (char *)context, response->code);
}

//断开连接成功回调函数
void on_discon(void* context, MQTTAsync_successData* response)
{
printf("disconnect success\r\n");
}

//断开连接失败回调函数
void on_disconfail(void* context,  MQTTAsync_failureData* response)
{
printf("disconnect failure: %d\r\n", response->code);
}

int main(int argc, char * argv[])
{
int ret=0;
MQTTAsync client;                                                               //客户端句柄
MQTTAsync_connectOptions con_opts=MQTTAsync_connectOptions_initializer;         //连接选项
MQTTAsync_disconnectOptions discon_opts=MQTTAsync_disconnectOptions_initializer;
MQTTAsync_willOptions will_opts=MQTTAsync_willOptions_initializer;              //遗嘱选项
MQTTAsync_responseOptions pub_resp_opts=MQTTAsync_responseOptions_initializer;  //发布结果
MQTTAsync_responseOptions sub_resp_opts=MQTTAsync_responseOptions_initializer;  //订阅结果
MQTTAsync_message mess=MQTTAsync_message_initializer;                           //发布消息结构体

/* 创建MQTT对象,若创建成功client不再是一个空指针*/
ret = MQTTAsync_create(&client, SERVER_ADDRESS, CLIENT_ID, MQTTCLIENT_PERSISTENCE_NONE, NULL);
if(ret!=MQTTASYNC_SUCCESS) {
printf("client creat error\r\n");
return -1;
}
printf("creat success\r\n");

/* 设置回调函数*/
ret = MQTTAsync_setCallbacks(client, NULL, cntlost, messarri, delcomp);
if(ret!=MQTTASYNC_SUCCESS) {
printf("set callback error\r\n");
goto CREAT_ERROR;
}

/* 设置连接函数,连接到指定的MQTT服务器*/
//1.配置遗嘱参数
will_opts.topicName="zyx_topic/will";
will_opts.qos=1;
will_opts.retained=1;
will_opts.message="dev unexpected disconnect";  //设备意外掉线
//2.配置连接参数
con_opts.keepAliveInterval=45;                  // 心跳时间间隔,单位s
con_opts.cleansession=0;                        // 不清除会话,接收离线信息
con_opts.will=&will_opts;
con_opts.username=USER_NAME;
con_opts.password=PASSWORD;
con_opts.connectTimeout=30;                      //连接时间,默认是30s,这里和默认一致
con_opts.onSuccess=on_connect;
con_opts.onFailure=on_connectFail;
//3.连接
ret = MQTTAsync_connect(client, &con_opts);
if(ret!=MQTTASYNC_SUCCESS) {
printf("mqtt connect error: %d\r\n", ret);
goto CREAT_ERROR;
}

sleep(10);

/* 发布:向遗嘱主题发布消息,表示设备上线*/
char message[20]={0};
memcpy(message, "dev connect", sizeof("dev connect"));
pub_resp_opts.onSuccess=on_send;
pub_resp_opts.onFailure=on_notsend;
pub_resp_opts.context="zyx_topic/will";
mess.payload=message;
mess.payloadlen=strlen(message);
mess.qos=1;
mess.retained=1;
ret = MQTTAsync_sendMessage(client, "zyx_topic/will", &mess, &pub_resp_opts);
if(ret!=MQTTASYNC_SUCCESS) {
printf("mqtt send error: %d\r\n", ret);
}

/* 订阅:订阅led主题*/
sub_resp_opts.onSuccess=on_subscribe;
sub_resp_opts.onFailure=on_dissubscribe;
sub_resp_opts.context="zyx_topic/led";
MQTTAsync_subscribe(client, "zyx_topic/led", 1, &sub_resp_opts);

for(;;) {
sleep(10);
}

/* 断开连接*/
//discon_opts.timeout=10;
discon_opts.onSuccess=on_discon;
discon_opts.onFailure=on_disconfail;
MQTTAsync_disconnect(client, &discon_opts);

CREAT_ERROR:
MQTTAsync_destroy(&client);
return -1;

EXIT:
return 0;
}
попробуйте
. Первое, что не пропагандируется, без очистки сообщения и topicname , не будет неисправности сегментации второй раз, введя функцию обратного вызова.
Английский не является моим нативным языком, поэтому я надеюсь, что я надеюсь, что это достаточно ясное. Спасибо за вашу помощь.

Подробнее здесь: https://stackoverflow.com/questions/797 ... ered-twice
Ответить

Быстрый ответ

Изменение регистра текста: 
Смайлики
:) :( :oops: :roll: :wink: :muza: :clever: :sorry: :angel: :read: *x)
Ещё смайлики…
   
К этому ответу прикреплено по крайней мере одно вложение.

Если вы не хотите добавлять вложения, оставьте поля пустыми.

Максимально разрешённый размер вложения: 15 МБ.

Вернуться в «Linux»