zhangmeng
2023-01-29 5fb901dd157b4a8bbfc3be916c6c1a9d02b5bfa6
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
#ifndef _c_bus_client_message_h_
#define _c_bus_client_message_h_
 
#include <stddef.h>
 
/*
    注册进程的proc信息,包括进程名[name], 进程[id],等
*/
typedef struct cproc cproc;
/*
    进程注册信息, 包括进程的proc信息 cproc
    待注册的本进程提供请求响应的主题 topics[s], char** rep, 主题数量 repcnt
    待注册的本进程发布的主题 topics[s], char** pub, 主题数量 pubcnt
    待注册的本进程订阅的主题 topics[s], char** sub, 主题数量 subcnt
    待注册的本进程订阅的[网络、远程主机]主题 topics[s], char** subnet, 主题数量 subnetcnt
*/
typedef struct creg creg;
 
//TableChanged enum pollcontrol 接收到的订阅消息,数据库的变化
enum TableChanged {
    T_Camera = 0,       //摄像机变化
    T_CameraRule = 1,       //摄像机任务参数变化
    T_Sdk = 2,      //sdk变化
    T_CameraPolygon = 3,        //摄像机多边形变化
    T_TimeRule = 4,     //时间规则变化
    T_Server = 5,       //服务器信息变化
    T_PollConfig = 6,       //轮询配置变化
    T_File = 7,     //本地文件变化
    T_FileSetting = 8,      //本地文件分析设置
    T_SdkChanSet = 9,       //算法通道设置变化
    T_FileStack = 10,       //数据栈变化
    T_ResourceConfig = 11,      //对外服务配置变化
    T_CalculationPower = 12,        //需要重新计算算力占用情况
    T_EventPush = 13,        //事件推送有变化
    T_Cluster = 14,      //集群创建、加入或退出
    T_CameraPolygonRelation = 15,        //摄像机区域的关联关系
    T_Voice = 16,       //报警声音发生变化
};
// pollcontrol 接收到的订阅消息,数据库的操作
enum DbAction {
    Insert = 0,     //Insert db
    Update = 1,     //Update db
    Delete = 2,     //Delete db
};
 
// 数据库变化信息
struct DbChangeMsg{
    TableChanged    table;     //变化的表
    char*           id;      //变化数据id
    size_t          idl;     // id len
    DbAction action;        //action/ DbAction[Insert/Update/Delete]
    char*           info;    //变化内容
    size_t          infol;
};
 
// 订阅消息, 包括数据库消息和其他进程的消息
struct csubmsg{
    char* topic;      // 收到的订阅消息的主题,区分那种订阅消息
    size_t topicl;
 
    // private
    // enum MsgT {NONE=0, DB, PROCLIST} type;
    char* msg;        // 收到的订阅消息的body
    size_t msgl;
};
 
// 其他进程信息, pollcontrol可能依赖其他进程的服务,可能需要等其他进程启动再开始工作
struct cclient{
    creg*  rinfo;               // 代表其他进程的进程信息
 
    int replykey;               // 没用,上一个版本用共享内存,此为key
    int hbcnt;                  // 心跳次数?可能没用
    int dcnt;                   // deadcount,可能没用?
    int status;                 // 进程状态,可能没用?
};
 
// 其他注册进程列表,如数据库进程需要启动再运行pollcontrol逻辑
struct cproclist{
    struct  cclient* cli;   // 其他进程的列表
    size_t  count;          // 其他进程的列表的count
};
 
//////////////////////////////////////////
// request msg
/*
    此消息既作为接收的request msg的结构,也作为发送request 消息的结构
    接收request消息会带有发出request消息的进程的id,procid
*/
struct creqmsg{
    char* procid;     // 发送request消息的进程id
    size_t procidl;
    char* msg;        // request消息体
    size_t msgl;
    char* path;
    size_t pathl;
    char* body;
    size_t bodyl;
};
// decode stack err msg
/*
    pollcontrol会接收数据栈解码发送的解码失败消息,用于置网页状态
*/
struct cstackmsgerr{
    char* stackid;    // 解码失败的数据栈id
    size_t stackidl;
    char* fileid;     // 解码失败的文件id
    size_t fileidl;
};
// stack file
/*
    数据栈的文件列表,对应 protomsg.FileAnalysis 但是此结构体非常长
    看代码应该只需要解析出的几个
*/
struct cstackfile{
    char* id;         // 文件id
    size_t idl;
    char* name;       // 文件name
    size_t namel;
    char* path;       // 文件路径
    size_t pathl;
 
    int type;               // 文件类型 1:video,2:picture
    void* noused;           // 未使用
};
// decode stack success msg
/*
    pollcontrol会接收数据栈解码完成的消息,然后下发新的数据栈任务
*/
struct cstackmsg{
    int procnum;                // decoder 启动的进程号,数据栈可能会有数个decoder同时运行
    char* stackid;        // 数据栈 id
    size_t stackidl;
    char* stackname;      // 数据栈 name
    size_t stacknamel;
    int type;                   // 数据栈类型 video picture
    int shmkey;                 // 数据栈使用的共享内存key
    int width;                  // 分辨率
    int height;
    int fps;                    // fps 采样 fps/s
    struct cstackfile* files;   // 数据栈文件列表
    size_t filescnt;
};
 
// reply msg
// 对应 bhome_msg.MsgRequestTopicReply
struct crepmsg{
    int errcode;                // 相应request请求的消息,错误码
    char* errmsg;         // 错误消息
    size_t errmsgl;
    char* data;           // 消息体
    size_t datal;
};
 
/*
    对应 bhome_msg.MsgQueryProcReply_Info query procs 返回值
*/
struct cqueryprocs{
    char* id;
    size_t idl;
    int online;
};
 
#ifdef __cplusplus
extern "C"{
#endif
 
/*
    内部使用,深拷贝 cproc
*/
cproc* internal_clone_cproc(const cproc* proc);
void internal_cproc_free(cproc* proc);
/*
    返回一个 cproc 结构,仅拷贝输入参数
    生命周期 cproc < name[id]
*/
cproc* make_cproc(const char* name, const char* id);
/*
    从已存在的 cproc 中获取 name 和 id,仅仅是 cproc 内部的引用,无需释放
    生命周期 name[id] < cproc
*/
char* cproc_name(const cproc* proc);
char* cproc_id(const cproc* proc);
/*
    释放 cproc 指针
*/
void cproc_free(cproc* proc);
 
/*
    返回一个 creg 结构,仅拷贝输入参数
    输入参数生命周期需覆盖返回值生命周期
*/
creg* make_creg(const cproc* proc, const char** rep, const size_t repcnt,
                                    const char** pub, const size_t pubcnt,
                                    const char** sub, const size_t subcnt,
                                    const char** subnet, const size_t subnetcnt);
creg* make_creg_from_cproc(const cproc* proc);
void creg_add_topic_reply(creg* reg, const char** topic, const size_t count);
void creg_add_topic_pub(creg* reg, const char** topic, const size_t count);
void creg_add_topic_sub(creg* reg, const char** topic, const size_t count);
void creg_add_topic_subnet(creg* reg, const char** topic, const size_t count);
/*
    获取已存在的 creg 中的 cproc 或者注册的主题,无需释放
    生命周期 < creg
*/
const cproc* creg_proc(const creg* reg);
char** creg_reply_topic(const creg* reg, size_t* count);
char** creg_pub_topic(const creg* reg, size_t* count);
char** creg_sub_topic(const creg* reg, size_t* count);
char** creg_subnet_topic(const creg* reg, size_t* count);
/*
    释放 creg 指针
*/
void creg_free(creg* reg);
 
// 订阅消息相关,订阅数据库db消息和进程列表proclist消息
/*
    cbhomeclient.cpp中使用,将接收到的submsg解包成csubmsg
    包括topic和msg数据,msg数据并未反序列化
    必须使用free_submsg释放
*/
struct csubmsg* to_submsg(const char* data, const size_t size);
void free_submsg(struct csubmsg* msg);
// db msg
/*
    接收到的submsg在pollcontrol中可能为数据库更新的通知
    将csubmsg中未反序列化的数据解包成db的数据格式
    必须用free_submsg_db释放
*/
struct DbChangeMsg* get_submsg_db(struct csubmsg* msg);
void free_submsg_db(struct DbChangeMsg* msg);
// proclist msg
/*
    接收到的submsg在pollcontrol中可能为关心的其他进程的列表
    将csubmsg中未反序列化的数据解包成进程的列表
    必须用free_submsg_proclist释放
*/
struct cproclist* get_submsg_proclist(struct csubmsg* msg);
void free_submsg_proclist(struct cproclist* ppl);
 
// request msg
/*
    cbhomeclient.cpp中使用,将接收到的request请求数据解包成creqmsg
    包括request进程的procid和msg数据,msg数据并未反序列化
    必须使用free_reqmsg释放
*/
struct creqmsg* to_reqmsg(const char* pid,const size_t pids,const char* data,const size_t size);
void free_reqmsg(struct creqmsg* msg);
/*
    本进程向其他进程请求数据构建
    包括请求的主题topic和请求的数据body[data]
    必须使用free_reqmsg释放
*/
struct creqmsg* make_req_msg(const char* topic, const size_t topicl,
                                const char* data, const size_t datal);
 
// decode err msg
/*
    接收到的creqmsg在pollcontrol中可能为数据栈解码错误信息
    将creqmsg中未反序列化的数据解包成cstackmsgerr,包括数据栈id stackid和文件id fileid
    必须用free_reqmsg_stackerr释放
*/
struct cstackmsgerr* get_reqmsg_stackerr(struct creqmsg* msg);
void free_reqmsg_stackerr(struct cstackmsgerr* msg);
// decode success msg
/*
    接收到的creqmsg在pollcontrol中可能为数据栈解码完成信息
    将creqmsg中未反序列化的数据解包成cstackmsg
    包括
    int procnum;    // 启动的decoder进程num
    struct cstr stackid;
    struct cstr stackname;
    int type;   // video picture
    int shmkey;
    int width;
    int height;
    int fps;
    struct cstackfile* files; // 文件列表
    size_t filescnt; // 文件数量
    必须用free_reqmsg_stackerr释放
*/
struct cstackmsg* get_reqmsg_stack(struct creqmsg* msg);
void free_reqmsg_stack(struct cstackmsg* msg);
 
// reply msg
/*
    创建 creqmsg 包括errcode、errmsg和消息体data
    必须使用 free_reply_msg 释放
*/
struct crepmsg* make_reply_msg(const int errcode, const char* errmsg, const size_t emsgl,
                                const char* data, const size_t datal);
void free_reply_msg(struct crepmsg* msg);
 
/*
    释放 query procs 从center获取所有的procs信息
*/
void free_query_procs(struct cqueryprocs* procs, const size_t count);
 
#ifdef __cplusplus
}
#endif
#endif