调试时发现的一个奇怪的现象,static int = 0时无法自增

本文探讨了一个关于正则表达式匹配图片URL的函数中出现的诡异现象:静态变量count始终显示为0,直到其初始值被设置为非0值。通过分析,发现了问题的根源在于sizeof操作符的误用,并解释了这一错误如何影响了静态变量的行为。
void Regex(char* buf) {
    char pattern[512]="<img\\ssrc=\"http://(\\S+.jpg)";
    static regmatch_t pm[2];
    static size_t nmatch = sizeof(pm);//这里的我本想得到2这个值,下面的注释才是正确的写法
    //static size_t nmatch = sizeof(pm)/sizeof(regmatch_t);
    regex_t reg;
    if (0 != regcomp(&reg,pattern,REG_EXTENDED)) {
        cout<<"regcomp error"<<endl;
        return ;
    }
    int offset = 0;
    while (0 == regexec(&reg,buf + offset,nmatch,pm,REG_NOTBOL)) {
        string strTemp;
        strTemp.insert(0, buf + offset + pm[0].rm_so, pm[0].rm_eo - pm[0].rm_so );
        cout<<strTemp<<endl;
        offset += pm[0].rm_eo + 1;
        static int count = 0;
        ++count;
        cout<<"count = "<<count<<endl;
    }
    regfree(&reg);
    return  ;
}

今天调代码时惊奇的发现,多次调用该函数,结果 static int count 的输出一直为0,感觉很诡异,然后又把count的初值改为非0值,结果count的输出就正常了, 不过这更让我费解,到底是为什么?最开始还怀疑是编译器的问题;
细心查找后才发现问题的原因所在:
是因为sizeof(pm) 的原因,这句本应该写为sizeof(pm)/sizeof(regmatch_t); 代码逻辑才正确。
虽然在这段代码中 static count 的值不能正常递增的原因找到了,但是其根本是什么原因呢?
是因为内存越界了吗?
是处在编译的问题吗?
为什么count初值不设为0时就能正常递增呢?

如果您明白,请指导一下!感谢

/* *MQTT 数据库存储MQTT未发布消息的表头格式 *id(INTEGER) | timestamp(DATETIME) | sent_flag(INTEGER) | topic(TEXT) | payload(TEXT) *id:用于唯一标识 *timestamp:间戳用于记录存储间 *pub:用于标记是否完成MQTT补发(0:未发布;1:已发布) *topic:存储的MQTT的主题 *payload:存储的MQTT的Payload内容 */ /*=========================================================================== include files ===/ #include <stdio.h> #include <stdlib.h> #include <string.h> #include <sqlite3.h> #include <stdbool.h> #include <time.h> #include <unistd.h> #include <sys/stat.h> #include <sys/types.h> #include <dirent.h> #include <pthread.h> #include “mqtt.h” #include “uart_command.h” #include “…/platform/queue_buffer.h” #include “…/bms_info_data/bms_info_data.h” #include “…/platform/syslog/logger.h” / Macro Definition ========================================================================/ #define MQTT_PUB_DB_MAX_QUEUE_LIMIT 3 #define MQTT_PUB_DB_DIR “/opt/database/” #define MQTT_PUB_DB_NAME “/opt/database/mqtt_pub_history.db” #define MQTT_PUB_TABLE_CREATE_SQL “CREATE TABLE IF NOT EXISTS mqtt_pub_msg (id INTEGER PRIMARY KEY AUTOINCREMENT, timestamp text,sent_flag INTEGER DEFAULT 0, topic TEXT, payload TEXT);” #define MQTT_PUB_MSG_INSERT_SQL “INSERT INTO mqtt_pub_msg (timestamp, topic, payload) VALUES (?, ?, ?);” #define MQTT_PUB_SELECT_OLDEST_UNSENT_MSG_SQL “SELECT id, timestamp, sent_flag, topic FROM mqtt_pub_msg WHERE sent_flag = 0 ORDER BY timestamp ASC LIMIT 1;” #define MQTT_PUB_UPDATE_OLDEST_UNSENT_FLAG_SQL “UPDATE mqtt_pub_msg SET sent_flag = 1 WHERE id = ? AND topic = ?;” #define MQTT_PUB_DROP_TABLE_SQL “DROP TABLE IF EXISTS mqtt_pub_msg;VACUUM;” /*======================================================================== Enumeration Definition ========================================================================/ /*======================================================================== Type Definition =========================================================================/ /*======================================================================== Global Variable ========================================================================/ static sqlite3 * mqtt_pub_db = NULL; static bool db_initialized = false; static pthread_mutex_t mqtt_pub_db_mutex = PTHREAD_MUTEX_INITIALIZER; QueueList mqtt_db_store_queue = {0}; pthread_mutex_t mqtt_db_store_queue_mutex = PTHREAD_MUTEX_INITIALIZER; /*======================================================================== function Definition ========================================================================/ bool mqtt_pub_db_initialized(void){ return db_initialized; } int mqtt_pub_db_dir_create(void) { int ret = 0; DIR *dir = NULL; if(NULL == (dir = opendir(MQTT_PUB_DB_DIR))){ if (0 != (ret = mkdir(MQTT_PUB_DB_DIR,0777))){ LOG(LOG_ERR,“mkdir %s failed!,ret:%d!\n”,MQTT_PUB_DB_DIR,ret); } } if(NULL != dir){ closedir(dir); dir = NULL; } return ret; } // Initialize the SQLite database. int mqtt_pub_db_init(void) { char *err_msg = NULL; int rc = sqlite3_open(MQTT_PUB_DB_NAME, &mqtt_pub_db); if (rc) { LOG(LOG_ERR,“Can’t open database: %s\n”, sqlite3_errmsg(mqtt_pub_db)); return rc; } else { LOG(LOG_ERR,“Opened mqtt pub database successfully\n”); } rc = sqlite3_exec(mqtt_pub_db, MQTT_PUB_TABLE_CREATE_SQL, 0, 0, &err_msg); if (rc != SQLITE_OK) { LOG(LOG_ERR,"SQL error: %s\n", err_msg); sqlite3_free(err_msg); sqlite3_close(mqtt_pub_db); return rc; } else { if (NULL != err_msg){ sqlite3_free(err_msg); err_msg = NULL; } LOG(LOG_DEBUG,"Table created successfully\n"); db_initialized = 1; } return 0; } //-- 彻底删除表(含自ID重置) //DROP TABLE IF EXISTS mqtt_pub_msg; //CREATE TABLE IF NOT EXISTS mqtt_pub_msg (…); – 原建表语句 int mqtt_pub_db_drop_and_create_table(void) { char *err_msg = NULL; int rc = 0; if (1 != db_initialized) { LOG(LOG_ERR,“db_initialized error!\n”); return -1; } if (NULL == mqtt_pub_db){ LOG(LOG_ERR,“mqtt db handle is NULL!\n”); return -1; } pthread_mutex_lock(&mqtt_pub_db_mutex); db_initialized = false; rc = sqlite3_exec(mqtt_pub_db, MQTT_PUB_DROP_TABLE_SQL, 0, 0, &err_msg); if (rc != SQLITE_OK) { LOG(LOG_ERR,“SQL error: %s\n”, err_msg); sqlite3_free(err_msg); err_msg = NULL; sqlite3_close(mqtt_pub_db); pthread_mutex_unlock(&mqtt_pub_db_mutex); return rc; } else { if (NULL != err_msg){ sqlite3_free(err_msg); err_msg = NULL; } LOG(LOG_DEBUG,“Drop Table successfully\n”); } rc = sqlite3_exec(mqtt_pub_db, MQTT_PUB_TABLE_CREATE_SQL, 0, 0, &err_msg); if (rc != SQLITE_OK) { LOG(LOG_ERR,"SQL error: %s\n", err_msg); sqlite3_free(err_msg); sqlite3_close(mqtt_pub_db); pthread_mutex_unlock(&mqtt_pub_db_mutex); return rc; } else { if (NULL != err_msg){ sqlite3_free(err_msg); err_msg = NULL; } LOG(LOG_DEBUG,"Table created successfully\n"); db_initialized = 1; } pthread_mutex_unlock(&mqtt_pub_db_mutex); return 0; } /* table name:mqtt_pub_msg table header:id(INTEGER) | timestamp(DATETIME) | sent_flag(INTEGER) | topic(TEXT) | payload(TEXT) */ // Store a message in the SQLite database. int mqtt_pub_db_msg_store(const char *topic, const char *message) { int ret = 0; sqlite3_stmt *stmt; const char sql = MQTT_PUB_MSG_INSERT_SQL; time_t now = time(NULL); struct tm local_buf; struct tm * local = localtime_r(&now,&local_buf); char timestamp[64] = {0}; strftime(timestamp, sizeof(timestamp), “%Y-%m-%d %H:%M:%S”, local); if ((NULL == topic) || (NULL == message)){ LOG(LOG_ERR,“param pointer is NULL!\n”); return -1; } if (!db_initialized) { LOG(LOG_ERR,“db_initialized error!\n”); return -1; } pthread_mutex_lock(&mqtt_pub_db_mutex); if ((NULL != strstr(topic,MQTT_PUB_TOPIC_SUFFIX_SYS)) || (NULL != strstr(topic,MQTT_PUB_TOPIC_SUFFIX_PCS)) || (NULL != strstr(topic,MQTT_PUB_TOPIC_SUFFIX_BMS)) || (NULL != strstr(topic,MQTT_PUB_TOPIC_SUFFIX_CHR)) || (NULL != strstr(topic,MQTT_PUB_TOPIC_SUFFIX_AIR)) || (NULL != strstr(topic,MQTT_PUB_TOPIC_SUFFIX_FPE)) || (NULL != strstr(topic,MQTT_PUB_TOPIC_SUFFIX_IO)) || (NULL != strstr(topic,MQTT_PUB_TOPIC_SUFFIX_DG)) || (NULL != strstr(topic,MQTT_PUB_TOPIC_SUFFIX_LTE))|| (NULL != strstr(topic,MQTT_PUB_TOPIC_SUFFIX_PV))) { LOG(LOG_DEBUG,“topic:%s pub storage to database!\n”,topic); sqlite3_prepare_v2(mqtt_pub_db, sql, -1, &stmt, NULL); /sqlite3_stmt:准备好的语句对象/ sqlite3_bind_text(stmt, 1, timestamp, -1, SQLITE_STATIC); sqlite3_bind_text(stmt, 2, topic, -1, SQLITE_STATIC); sqlite3_bind_text(stmt, 3, message, -1, SQLITE_STATIC); if (sqlite3_step(stmt) != SQLITE_DONE) { LOG(LOG_ERR,"SQL error: %s\n", sqlite3_errmsg(mqtt_pub_db)); ret = -1; } sqlite3_finalize(stmt);/*使用sqlite3_prepare_v2准备语句对象,在使用完成后要调用sqlite3_finalize释放资源*/ } pthread_mutex_unlock(&mqtt_pub_db_mutex); return ret; } /删除超出指定间范围的数据。例如,删除早于 7 天前的数据/ void mqtt_pub_db_delete_old_data(sqlite3 *db, int days) { char sql[256]; time_t now = time(NULL); struct tm local_buf; struct tm *local = localtime_r(&now,&local_buf); char datetime[64]; if (NULL == db){ LOG(LOG_ERR,“db pointer is NULL!\n”); return; } if (!db_initialized) { LOG(LOG_ERR,“db_initialized error!\n”); return; } strftime(datetime, sizeof(datetime), “%Y-%m-%d %H:%M:%S”, local); // Calculate the date and time for the cutoff local->tm_mday -= days; mktime(local); // Normalize the time struct strftime(datetime, sizeof(datetime), "%Y-%m-%d %H:%M:%S", local); snprintf(sql, sizeof(sql), "DELETE FROM mqtt_pub_msg WHERE timestamp < '%s';", datetime); char *errmsg = NULL; int rc = sqlite3_exec(db, sql, 0, 0, &errmsg); if (rc != SQLITE_OK) { LOG(LOG_ERR,"SQL error: %s\n", errmsg); sqlite3_free(errmsg); } else { if (NULL != errmsg){ sqlite3_free(errmsg); errmsg = NULL; } LOG(LOG_DEBUG,"Old data deleted successfully\n"); } } void mqtt_pub_db_send_cmd(long id,const unsigned char * topic) { module_mqtt_topic_pub_db_cmd_info_t mqtt_pub_db_cmd_info = {0}; if (NULL == topic){ fprintf(stderr, “topic is NULL!”); return; } memset(&mqtt_pub_db_cmd_info,0x00,sizeof(module_mqtt_topic_pub_db_cmd_info_t)); mqtt_pub_db_cmd_info.mqtt_pub_msg_db_id = id; strcpy(mqtt_pub_db_cmd_info.mqtt_pub_msg_db_topic,(char*)topic); send_module_cmd_data(STAT_SET_MQTT_PUB_DB,(uint8_t*)&mqtt_pub_db_cmd_info,sizeof(module_mqtt_topic_pub_db_cmd_info_t)); return; } /* table name:mqtt_pub_msg table header:id(INTEGER) | timestamp(DATETIME) | sent_flag(INTEGER) | topic(TEXT) | payload(TEXT) */ // Resend the oldest message from the database. int mqtt_db_send_oldest_msg_cmd(void) { sqlite3_stmt *stmt; const char *sql = MQTT_PUB_SELECT_OLDEST_UNSENT_MSG_SQL; //printf(“enter into %s,db_initialized:%d\n”,func,db_initialized); if (!db_initialized) { LOG(LOG_ERR,“db_initialized error!\n”); return -1; } //printf(“%s db_initialized!\n”,func); pthread_mutex_lock(&mqtt_pub_db_mutex); if (sqlite3_prepare_v2(mqtt_pub_db, sql, -1, &stmt, NULL) != SQLITE_OK){ LOG(LOG_ERR,“Failed to prepare SELECT statement\n”); pthread_mutex_unlock(&mqtt_pub_db_mutex); return -1; } while (sqlite3_step(stmt) == SQLITE_ROW) { long id = sqlite3_column_int64(stmt, 0); const unsigned char *timestamp = sqlite3_column_text(stmt, 1); const unsigned char *topic = sqlite3_column_text(stmt, 3); LOG(LOG_DEBUG,"history mqtt pub msg send:id:[%ld] timestamp:[%s] topic:[%s]\n",id,timestamp,topic); mqtt_pub_db_send_cmd(id,topic); break; } sqlite3_finalize(stmt); pthread_mutex_unlock(&mqtt_pub_db_mutex); return 0; } int mqtt_db_send_msg_by_id_topic(long id,char * topic,char ** dst_str,uint16_t * dst_len) { int ret = 0; char *query = “SELECT payload FROM mqtt_pub_msg WHERE id = ? AND topic = ? AND sent_flag = 0;”; sqlite3_stmt *stmt; if(NULL == topic){ LOG(LOG_ERR,“topic is NULL!\n”); return -1; } if (!db_initialized) { LOG(LOG_ERR,“db_initialized error!\n”); return -1; } pthread_mutex_lock(&mqtt_pub_db_mutex); // Prepare the SELECT statement if (sqlite3_prepare_v2(mqtt_pub_db, query, -1, &stmt, NULL) != SQLITE_OK) { LOG(LOG_ERR,“Failed to prepare SELECT statement\n”); pthread_mutex_unlock(&mqtt_pub_db_mutex); return -1; } // Bind the id to the SELECT statement sqlite3_bind_int64(stmt, 1, id); sqlite3_bind_text(stmt, 2, topic, -1, SQLITE_STATIC); // Execute the SELECT statement if (sqlite3_step(stmt) == SQLITE_ROW) { const unsigned char *payload = sqlite3_column_text(stmt, 0); int payload_len = sqlite3_column_bytes(stmt, 0); if (NULL == (dst_str = (char)calloc(1,payload_len+1))){ ret = -1; *dst_len = 0; }else { memcpy(*dst_str,payload,payload_len); *dst_len = (uint16_t)payload_len; ret = 0; } } else { LOG(LOG_ERR,“No record found with id %ld\n”, id); sqlite3_finalize(stmt); pthread_mutex_unlock(&mqtt_pub_db_mutex); return -1; } // Finalize the SELECT statement sqlite3_finalize(stmt); pthread_mutex_unlock(&mqtt_pub_db_mutex); return ret; } void mqtt_db_query_and_update_sent_flag(long id,char * topic) { char *query = “SELECT sent_flag FROM mqtt_pub_msg WHERE id = ? AND topic = ?;”; char *update_query = “UPDATE mqtt_pub_msg SET sent_flag = 1 WHERE id = ? AND topic = ?;”; sqlite3_stmt *stmt; sqlite3_stmt *update_stmt; int sent_flag = 0; if(NULL == topic){ LOG(LOG_ERR,"topic is NULL!\n"); return; } if (!db_initialized) { LOG(LOG_ERR,"db_initialized error!\n"); return; } pthread_mutex_lock(&mqtt_pub_db_mutex); // Prepare the SELECT statement if (sqlite3_prepare_v2(mqtt_pub_db, query, -1, &stmt, NULL) != SQLITE_OK) { pthread_mutex_unlock(&mqtt_pub_db_mutex); LOG(LOG_ERR,"Failed to prepare SELECT statement\n"); return; } // Bind the id to the SELECT statement sqlite3_bind_int64(stmt, 1, id); sqlite3_bind_text(stmt, 2, topic, -1, SQLITE_STATIC); // Execute the SELECT statement if (sqlite3_step(stmt) == SQLITE_ROW) { sent_flag = sqlite3_column_int(stmt, 0); } else { LOG(LOG_ERR,"No record found with id %ld\n", id); sqlite3_finalize(stmt); pthread_mutex_unlock(&mqtt_pub_db_mutex); return; } // Finalize the SELECT statement sqlite3_finalize(stmt); // Check the sent_flag value if (sent_flag == 0) { // Prepare the UPDATE statement if (sqlite3_prepare_v2(mqtt_pub_db, update_query, -1, &update_stmt, NULL) != SQLITE_OK) { LOG(LOG_ERR,"Failed to prepare UPDATE statement\n"); pthread_mutex_unlock(&mqtt_pub_db_mutex); return; } // Bind the message_id to the UPDATE statement sqlite3_bind_int64(update_stmt, 1, id); sqlite3_bind_text(stmt, 2, topic, -1, SQLITE_STATIC); // Execute the UPDATE statement if (sqlite3_step(update_stmt) != SQLITE_DONE) { LOG(LOG_ERR,"Failed to update sent_flag for id %ld\n", id); } // Finalize the UPDATE statement sqlite3_finalize(update_stmt); LOG(LOG_DEBUG,"Successfully updated sent_flag for message id %ld\n", id); } else { LOG(LOG_DEBUG,"Message id %ld has already been sent\n", id); } pthread_mutex_unlock(&mqtt_pub_db_mutex); } // Resend the oldest message from the database. int mqtt_db_oldest_msg_send_cmd(void) { if (!db_initialized) { fprintf(stderr, “%s db_initialized error!\n”,func); return -1; } sqlite3_stmt *stmt; const char *sql = MQTT_PUB_SELECT_OLDEST_UNSENT_MSG_SQL; pthread_mutex_lock(&mqtt_pub_db_mutex); sqlite3_prepare_v2(mqtt_pub_db, sql, -1, &stmt, NULL); while (sqlite3_step(stmt) == SQLITE_ROW) { long id = sqlite3_column_int64(stmt, 0); const unsigned char * datetime = sqlite3_column_text(stmt, 1); int sent_flag = sqlite3_column_int(stmt, 2); const unsigned char *topic = sqlite3_column_text(stmt, 3); const unsigned char *message = sqlite3_column_text(stmt, 4); LOG(LOG_DEBUG,"history mqtt pub msg:id:[%ld] datatime:[%s] sent_flag:[%d] topic:[%s] payload:[%s]\n",id,datetime,sent_flag,topic,message); mqtt_pub_db_send_cmd(id,topic); break; } sqlite3_finalize(stmt); pthread_mutex_unlock(&mqtt_pub_db_mutex); return 0; } void * mqtt_pub_db_process_thread_entry(void * arg) { int ret = 0; unsigned int count = 0; int module_cmd_queue_num = 0; ec600u_mqtt_client_connect_state_t mqtt_cli_conn_state = {0}; OtherDevInfo_Core2Core other_dev_info = {0}; memset(&other_dev_info,0x00,sizeof(OtherDevInfo_Core2Core)); ret = mqtt_pub_db_dir_create(); if (0 != ret){ LOG(LOG_ERR,“create directory %s err!”,MQTT_PUB_DB_DIR); goto exit_mqtt_pub_db_process_thread; } //sqlite3_config(SQLITE_CONFIG_MULTITHREAD);//设置SQLite为多线程模式 sqlite3_config(SQLITE_CONFIG_SERIALIZED); // 设置为串行数据库 ret = mqtt_pub_db_init(); if (0 != ret){ LOG(LOG_ERR,"create database:%s err!",MQTT_PUB_DB_NAME); goto exit_mqtt_pub_db_process_thread; } while(1){ if (count % 1 == 0){ get_module_mqtt_cli_conn_state(&mqtt_cli_conn_state); if (1 == mqtt_cli_conn_state.mqtt_connect_state){ module_cmd_queue_num = get_module_cmd_queue_num(); if (module_cmd_queue_num <= MQTT_PUB_DB_MAX_QUEUE_LIMIT){ /*发送历史数据*/ mqtt_db_send_oldest_msg_cmd(); } } } if (count % 60 == 0){ //1分钟检测一次并删除超出7天的历史数据 count = 0; /*删除7天前的历史数据*/ pthread_mutex_lock(&mqtt_pub_db_mutex); mqtt_pub_db_delete_old_data(mqtt_pub_db,7); pthread_mutex_unlock(&mqtt_pub_db_mutex); } get_r_core_R2A_OtherDev_info(&other_dev_info); if (0x5A == other_dev_info.data[910]){ /*Offset 910 for clean mqtt*/ mqtt_pub_db_drop_and_create_table(); } count++; sleep(1); } exit_mqtt_pub_db_process_thread: LOG(LOG_ERR,“exit”); sqlite3_close(mqtt_pub_db); pthread_exit(NULL); } int cmd_prot_msg_pack(uint8_t *data,uint16_t data_len,module_cmd_type_e cmd_type,uint8_t * output,uint32_t *output_len) { module_cmd_prot_t cmd_prot_info = {0}; if (NULL == output) return -1; //printf(“Enter into %s func\n”,func); memset(&cmd_prot_info, 0, sizeof(module_cmd_prot_t)); cmd_prot_info.cmd_type = cmd_type; cmd_prot_info.data_len = data_len; memcpy(output, &cmd_prot_info, MODULE_CMD_PROT_HEAD_LEN); if ((data != NULL) && (data_len > 0)) { memcpy(output + MODULE_CMD_PROT_HEAD_LEN, data, data_len); } *output_len = MODULE_CMD_PROT_HEAD_LEN + data_len; return 0; } int mqtt_offline_db_store_enqueue(void *ctx) { int ret = 0; ligoo_msg_info_s *info = (ligoo_msg_info_s *)ctx; ligoo_msg_info_s msg_info = {0}; msg_info.data = info->data; msg_info.data_len = info->data_len; LOG(LOG_DEBUG,"Enter into %s,module_cmd_queue num:%d\n",__func__,num_queue(&mqtt_db_store_queue)); pthread_mutex_lock(&mqtt_db_store_queue_mutex); if (0 != enqueue(msg_info.data,msg_info.data_len , &mqtt_db_store_queue)) { LOG(LOG_ERR,"enqueue failed!\n"); ret = -1; } if (NULL != msg_info.data){ free(msg_info.data); } pthread_mutex_unlock(&mqtt_db_store_queue_mutex); return ret; } /* *input para1:unsigned char * data *input para2:unsigned int data_len *input para3:unsigned char cmd_type * *return param:int */ int mqtt_offline_db_store_cmd_data(module_cmd_type_e cmd_type,unsigned char * data,unsigned int data_len) { int ret = 0; ligoo_msg_info_s msg_info ={0}; msg_info.data_len = data_len + MODULE_CMD_PROT_HEAD_LEN; msg_info.data = (unsigned char )calloc(1,msg_info.data_len); cmd_prot_msg_pack(data,data_len,cmd_type,msg_info.data,&msg_info.data_len); ret = mqtt_offline_db_store_enqueue((void)&msg_info); return ret; } void * mqtt_pub_db_db_store_process_thread_entry(void * arg) { int ret =0; ligoo_msg_info_s msg_info = {0}; module_cmd_prot_t module_cmd_prot_info = {0}; char * payload_json_object = NULL; uint16_t payload_json_object_len = 0; ligoo_mqtt_pub_send_topic_t mqtt_pub_send_topic = {0}; module_mqtt_topic_pub_cmd_info_t module_mqtt_topic_pub_cmd_info = {0}; ec600u_mqtt_client_connect_state_t mqtt_cli_conn_state = {0}; module_mqtt_topic_pub_info_t module_mqtt_topic_pub_info = {0}; LOG(LOG_DEBUG,“Enter\n”); init_queue(&mqtt_db_store_queue); while(1) { if(is_empty(&mqtt_db_store_queue)) { usleep(100000); continue; } memset(&msg_info,0x00,sizeof(ligoo_msg_info_s)); memset(&module_cmd_prot_info,0x00,sizeof(module_cmd_prot_t)); if (NULL != (msg_info.data = get_head(&mqtt_db_store_queue))) { if ((msg_info.data_len = get_head_len(&mqtt_db_store_queue)) < 0) { pthread_mutex_lock(&mqtt_db_store_queue_mutex); dequeue(&mqtt_db_store_queue); pthread_mutex_unlock(&mqtt_db_store_queue_mutex); continue; } memcpy(&module_cmd_prot_info,msg_info.data,MODULE_CMD_PROT_HEAD_LEN); if (msg_info.data_len == module_cmd_prot_info.data_len + MODULE_CMD_PROT_HEAD_LEN){ module_cmd_prot_info.data = msg_info.data + MODULE_CMD_PROT_HEAD_LEN; }else { pthread_mutex_lock(&mqtt_db_store_queue_mutex); dequeue(&mqtt_db_store_queue); pthread_mutex_unlock(&mqtt_db_store_queue_mutex); continue; } LOG(LOG_DEBUG,“process module cmd:%d\n”,module_cmd_prot_info.cmd_type); switch(module_cmd_prot_info.cmd_type){ case STAT_SET_MQTT_PUB:{ memset(&module_mqtt_topic_pub_cmd_info,0x00,sizeof(module_mqtt_topic_pub_cmd_info_t)); memset(&module_mqtt_topic_pub_info,0x00,sizeof(module_mqtt_topic_pub_info_t)); memset(&mqtt_pub_send_topic,0x00,sizeof(ligoo_mqtt_pub_send_topic_t)); if (module_cmd_prot_info.data_len == sizeof(module_mqtt_topic_pub_cmd_info_t)){ memcpy(&module_mqtt_topic_pub_cmd_info,module_cmd_prot_info.data,module_cmd_prot_info.data_len); }else { break; } ret = get_mqtt_topic_pub_info_cb_process(module_mqtt_topic_pub_cmd_info.param_id,module_mqtt_topic_pub_cmd_info.topic_suffix,&module_mqtt_topic_pub_info); if (0 == ret){ mqtt_pub_send_topic.qos = module_mqtt_topic_pub_info.qos; get_mqtt_pub_topic_prefix(mqtt_pub_send_topic.topic,MQTT_TOPIC_CONTAIN_MAX_LEN); strcat(mqtt_pub_send_topic.topic,module_mqtt_topic_pub_info.topic_suffix); LOG(LOG_DEBUG,“mqtt pub topic:%s\n”,mqtt_pub_send_topic.topic); mqtt_pub_send_topic.topic_len = strlen(mqtt_pub_send_topic.topic); payload_json_object = module_mqtt_topic_pub_info.pub_payload_json_cb(module_mqtt_topic_pub_cmd_info.param_id); if (NULL == payload_json_object){ LOG(LOG_DEBUG,“payload_json_object is NULL!\n”); break; } payload_json_object_len = strlen(payload_json_object); LOG(LOG_DEBUG,“mqtt pub topic payload:[%s] payload len:[%d]\n”,payload_json_object,payload_json_object_len); get_module_mqtt_cli_conn_state(&mqtt_cli_conn_state); LOG(LOG_DEBUG,“mqtt broker disconnected:%d!store into db!\n”,mqtt_cli_conn_state.mqtt_connect_state); mqtt_pub_db_msg_store(mqtt_pub_send_topic.topic,payload_json_object); if(payload_json_object){ free(payload_json_object); payload_json_object = NULL; } break; } break; } default:{ break; } } } pthread_mutex_lock(&mqtt_db_store_queue_mutex); dequeue(&mqtt_db_store_queue); pthread_mutex_unlock(&mqtt_db_store_queue_mutex); } pthread_exit(NULL); } 请分析以上代码是否存在内存泄露问题?如果内存请指出对应代码位置,并给出修改方案。
07-12
#include <stdio.h> #include <string.h> // 配置参数 #define TIME_OUT 10 // 超阈值(500ms * 10 = 5s) #define PING_INTERVAL 10 // 保活周期(调用次数) #define PING_FAIL_THRESHOLD 3 // 保活失败重连阈值 #define RETURN_BUFF_SIZE 256 // 接收缓冲区大小 // 状态定义(使用宏代替枚举) #define STATE_WIFI_CONNECT 0 #define STATE_MQTT_CONNECT 1 #define STATE_MQTT_CONNACK 2 #define STATE_MQTT_SUBSCRIBE 3 #define STATE_MQTT_SUBACK 4 #define STATE_KEEP_ALIVE 5 #define STATE_RECEIVE_MSG 6 // 全局变量 static int state = STATE_WIFI_CONNECT; // 当前状态 static char count = 0; // 通用计数器 static char ping_fail_count = 0; // 保活失败计数器 static char ping_req_flag = 0; // 保活请求标志 static char wifi_state = 0; // WiFi连接状态 // 函数声明(需根据实际平台实现) int WIFI_Init(void); int MQTT_Connect(const char*, const char*, const char*, const char*, const char*, char, char, char, char, char, char, int); int MQTT_ConnAck(char*); int MQTT_Subscribe(const char*, int, char, char); int MQTT_SubAck(char*); void MQTT_PingREQ(void); int MQTT_PingResp(char*); int MQTT_ReceivelPublish(char*, char*, char*, int*, char*, char*, int); void MQTT_SendPubAck(int); void MQTT_SendPubRec(int); void MQTT_SendPubRel(int); void MQTT_SendPubComp(int); int MQTT_ReceivePubAck(char*); int MQTT_ReceivePubRec(char*); int MQTT_ReceivePubRel(char*); int MQTT_ReceivePubComp(char*); int MQTT_UnSubAck(char*, int); void TIM4_Init(int, int); void Iot_Control(char*); void remove_from_retry_list(int); // 主状态机函数 void Aliyun_Iot(char *redata) { // 全局超保护 static char global_timeout = 0; global_timeout++; if (global_timeout > TIME_OUT * 2) { printf("\n[ERROR] 全局超!重置状态机\n"); state = STATE_WIFI_CONNECT; count = ping_fail_count = ping_req_flag = 0; global_timeout = 0; return; } // 计数器自(在状态切换重置) count++; printf("\n计数器 %d, 状态 %d\n", count, state); switch (state) { case STATE_WIFI_CONNECT: // 0: WiFi连接 printf("\n正在连接 WiFi...\n"); if (WIFI_Init() == 0) { TIM4_Init(10 - 1, 7200 - 1); wifi_state = 1; state = STATE_MQTT_CONNECT; count = 0; // 重置计数器 printf("WiFi连接成功\n"); } break; case STATE_MQTT_CONNECT: // 1: MQTT连接 printf("发送MQTT连接请求...\n"); if (MQTT_Connect("clientid", "username", "password", "will_topic", "will_message", 1, 1, 0, 1, 1, 1, 60) == 0) { state = STATE_MQTT_CONNACK; count = 0; printf("等待连接响应\n"); } break; case STATE_MQTT_CONNACK: // 2: 等待连接确认 if (count >= TIME_OUT) { printf("[WARN] MQTT连接超\n"); state = STATE_MQTT_CONNECT; count = 0; break; } if (MQTT_ConnAck(redata) == 1) { state = STATE_MQTT_SUBSCRIBE; count = 0; printf("订阅主题\n"); } break; case STATE_MQTT_SUBSCRIBE: // 3: 订阅主题 printf("发送订阅请求...\n"); if (MQTT_Subscribe("topic", 123, 0, 1) == 0) { state = STATE_MQTT_SUBACK; count = 0; printf("等待订阅确认\n"); } break; case STATE_MQTT_SUBACK: // 4: 等待订阅确认 if (count >= TIME_OUT) { printf("[WARN] 订阅超\n"); state = STATE_MQTT_CONNECT; count = 0; break; } if (MQTT_SubAck(redata) == 1) { state = STATE_KEEP_ALIVE; count = 0; printf("订阅成功\n"); } break; case STATE_KEEP_ALIVE: // 5: 保活处理 // 保活周期检查 if (count >= PING_INTERVAL) { if (!ping_req_flag) { // 可以发送新PING MQTT_PingREQ(); ping_req_flag = 1; printf("发送心跳请求\n"); } else { // 已发送但未收到响应 ping_fail_count++; printf("[WARN] 心跳超!次数=%d\n", ping_fail_count); if (ping_fail_count >= PING_FAIL_THRESHOLD) { printf("[ERROR] 保活失败,重新连接\n"); state = STATE_MQTT_CONNECT; ping_fail_count = ping_req_flag = count = 0; break; } } count = 0; } // 继续处理消息 state = STATE_RECEIVE_MSG; break; case STATE_RECEIVE_MSG: // 6: 消息处理 // 无数据返回保活状态 if (!redata || redata[0] == 0) { state = STATE_KEEP_ALIVE; break; } // 处理MQTT消息 switch (redata[0] >> 4) { case 3: { // PUBLISH消息 char qos, dup, retain; int id; char buf[RETURN_BUFF_SIZE]; if (MQTT_ReceivelPublish(&dup, &qos, &retain, &id, redata, buf, RETURN_BUFF_SIZE) == 0) { printf("收到消息: %s\n", buf); Iot_Control(buf); if (qos == 1) MQTT_SendPubAck(id); else if (qos == 2) MQTT_SendPubRec(id); } count = 0; break; } case 4: // PUBACK if (int id = MQTT_ReceivePubAck(redata)) { remove_from_retry_list(id); count = 0; } break; case 5: // PUBREC if (int id = MQTT_ReceivePubRec(redata)) { remove_from_retry_list(id); MQTT_SendPubRel(id); count = 0; } break; case 6: // PUBREL if (int id = MQTT_ReceivePubRel(redata)) { MQTT_SendPubComp(id); count = 0; } break; case 7: // PUBCOMP if (int id = MQTT_ReceivePubComp(redata)) { remove_from_retry_list(id); count = 0; } break; case 11: // UNSUBACK if (MQTT_UnSubAck(redata, 123) == 1) { state = STATE_KEEP_ALIVE; } else { MQTT_Subscribe("topic", 123, 0, 0); } count = 0; break; case 13: // PINGRESP if (MQTT_PingResp(redata) == 1) { printf("收到心跳响应\n"); ping_req_flag = 0; ping_fail_count = 0; count = 0; } break; default: break; } state = STATE_KEEP_ALIVE; break; default: printf("[ERROR] 未知状态,重置状态机\n"); state = STATE_WIFI_CONNECT; count = 0; break; } } 不需要CASE宏
07-14
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值