Line data Source code
1 : /**
2 : * Copyright (c) 2025 Huawei Technologies Co., Ltd.
3 : * This program is free software, you can redistribute it and/or modify it under the terms and conditions of
4 : * CANN Open Software License Agreement Version 2.0 (the "License").
5 : * Please refer to the License for details. You may not use this file except in compliance with the License.
6 : * THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND, EITHER EXPRESS OR IMPLIED,
7 : * INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT, MERCHANTABILITY, OR FITNESS FOR A PARTICULAR PURPOSE.
8 : * See LICENSE in the root of the software repository for the full text of the License.
9 : */
10 : #include "trace_server_mgr.h"
11 : #include "trace_system_api.h"
12 : #include "adiag_print.h"
13 : #include "trace_session_mgr.h"
14 : #include "trace_msg.h"
15 :
16 : #define MSG_STATUS_LONG_LINK 12
17 : #define MSG_STATUS_SHORT_LINK 13
18 :
19 : #define RECV_BUFF_SIZE (512 * 1024) // 512K
20 : #define MAX_RECV_TIMEOUT 3000 // timeout 3s
21 : typedef struct {
22 : unsigned short headInfo; // head magic data, judge to little
23 : unsigned char headVer; // head version
24 : unsigned char order; // packet order (reserved)
25 : unsigned short reqType; // request type of proto
26 : unsigned short devId; // request device Id
27 : unsigned int totalLen; // whole message length, only all data[0] length
28 : unsigned int sliceLen; // one slice length, only data[0] length
29 : unsigned int offset; // offset
30 : unsigned short msgType; // message type
31 : unsigned short status; // message status data
32 : unsigned char data[0]; // message data
33 : } TraceDataMsg;
34 :
35 15 : int32_t TraceDeviceInit(void) { return TRACE_SUCCESS; }
36 :
37 5 : STATIC TraStatus TraceHandleHelloMsg(const void* handle, const TraceHelloMsg* msg)
38 : {
39 5 : if ((msg->magic != TRACE_HEAD_MAGIC) || (msg->version != TRACE_HEAD_VERSION)) {
40 1 : ADIAG_ERR("msg head check failed, msg->magic=%u, msg->version=%u.", msg->magic, msg->version);
41 1 : return TRACE_FAILURE;
42 : }
43 :
44 : // get pid from handle
45 4 : int32_t pid = 0;
46 4 : int32_t rt = TraceAdxGetAttrByCommHandle(handle, HDC_SESSION_ATTR_PEER_CREATE_PID, &pid);
47 4 : if (rt != TRACE_SUCCESS) {
48 1 : ADIAG_ERR("get pid failed, ret = %d.", rt);
49 1 : return TRACE_FAILURE;
50 : }
51 3 : ADIAG_INF("hello msg pid = %d.", pid);
52 3 : TraceHelloMsg* sendMsg = NULL;
53 3 : sendMsg = (TraceHelloMsg*)AdiagMalloc(sizeof(TraceHelloMsg));
54 3 : if (sendMsg == NULL) {
55 1 : ADIAG_ERR("malloc failed.");
56 1 : return TRACE_FAILURE;
57 : }
58 2 : sendMsg->msgType = TRACE_HELLO_MSG;
59 2 : sendMsg->magic = TRACE_HEAD_MAGIC;
60 2 : sendMsg->version = TRACE_HEAD_VERSION;
61 : // short link need to send end msg
62 2 : TraStatus ret = TraceAdxSendMsg(handle, (const char*)sendMsg, (uint32_t)sizeof(TraceHelloMsg));
63 2 : TraStatus retEnd = TraceAdxSendMsg(handle, HDC_END_MSG, strlen(HDC_END_MSG));
64 2 : ADIAG_SAFE_FREE(sendMsg);
65 2 : if ((ret != TRACE_SUCCESS) || (retEnd != TRACE_SUCCESS)) {
66 1 : ADIAG_ERR("send hello msg failed.");
67 1 : return TRACE_FAILURE;
68 : }
69 1 : ADIAG_INF("send hello msg successfully.");
70 1 : return TRACE_SUCCESS;
71 : }
72 :
73 3 : STATIC TraStatus TraceHandleStartMsg(const void* handle, const TraceStartMsg* msg)
74 : {
75 : // get devId from handle
76 3 : int32_t devId = 0;
77 3 : TraStatus ret = TraceAdxGetAttrByCommHandle(handle, HDC_SESSION_ATTR_DEV_ID, &devId);
78 3 : if (ret != TRACE_SUCCESS) {
79 1 : ADIAG_ERR("get device id failed, ret = %d.", ret);
80 1 : return TRACE_FAILURE;
81 : }
82 :
83 : // get pid from handle
84 2 : int32_t pid = 0;
85 2 : ret = TraceAdxGetAttrByCommHandle(handle, HDC_SESSION_ATTR_PEER_CREATE_PID, &pid);
86 2 : if (ret != TRACE_SUCCESS) {
87 1 : ADIAG_ERR("get pid failed, ret = %d.", ret);
88 1 : return TRACE_FAILURE;
89 : }
90 1 : ret = TraceServerInsertSessionNode(handle, pid, devId, msg->timeout);
91 1 : if (ret != TRACE_SUCCESS) {
92 0 : return TRACE_FAILURE;
93 : }
94 1 : ADIAG_INF(
95 : "trace server insert session node successfully, pid = %d, devId = %d, msgtype = %d, timeout = %dms.", pid,
96 : devId, (int32_t)msg->msgType, msg->timeout);
97 1 : return TRACE_SUCCESS;
98 : }
99 :
100 6 : STATIC TraStatus TraceHandleLinkMsg(const void* handle)
101 : {
102 6 : uint32_t dataMaxLen = RECV_BUFF_SIZE;
103 6 : char* data = (char*)AdiagMalloc(dataMaxLen);
104 6 : if (data == NULL) {
105 2 : ADIAG_ERR("malloc failed, strerr = %s.", strerror(AdiagGetErrorCode()));
106 2 : TraceAdxDestroyCommHandle(handle);
107 2 : return TRACE_FAILURE;
108 : }
109 4 : TraStatus ret = TraceAdxRecvMsg(handle, &data, &dataMaxLen, MAX_RECV_TIMEOUT);
110 4 : if (ret != TRACE_SUCCESS) {
111 1 : ADIAG_ERR("adx receive message failed, ret = %d", ret);
112 1 : TraceAdxDestroyCommHandle(handle);
113 1 : ADIAG_SAFE_FREE(data);
114 1 : return TRACE_FAILURE;
115 : }
116 :
117 3 : ret = TraceHandleStartMsg(handle, (const TraceStartMsg*)data);
118 3 : ADIAG_SAFE_FREE(data);
119 3 : if (ret != TRACE_SUCCESS) {
120 2 : TraceAdxDestroyCommHandle(handle);
121 2 : return TRACE_FAILURE;
122 : }
123 1 : return TRACE_SUCCESS;
124 : }
125 :
126 4 : STATIC TraStatus TraceHandleEndMsg(const void* handle, const TraceEndMsg* msg)
127 : {
128 : (void)msg;
129 : // get devId from handle
130 4 : int32_t devId = 0;
131 4 : TraStatus ret = TraceAdxGetAttrByCommHandle(handle, HDC_SESSION_ATTR_DEV_ID, &devId);
132 4 : if (ret != TRACE_SUCCESS) {
133 1 : ADIAG_ERR("get device id failed, ret = %d.", ret);
134 1 : return TRACE_FAILURE;
135 : }
136 :
137 : // get pid from handle
138 3 : int32_t pid = 0;
139 3 : ret = TraceAdxGetAttrByCommHandle(handle, HDC_SESSION_ATTR_PEER_CREATE_PID, &pid);
140 3 : if (ret != TRACE_SUCCESS) {
141 1 : ADIAG_ERR("get pid failed, ret = %d.", ret);
142 1 : return TRACE_FAILURE;
143 : }
144 2 : ret = TraceServerDeleteSessionNode(handle, pid, devId);
145 2 : if (ret != TRACE_SUCCESS) {
146 1 : ADIAG_ERR("delete session node failed, ret = %d.", ret);
147 1 : return TRACE_FAILURE;
148 : }
149 :
150 1 : ADIAG_INF("delete session node successfully, pid = %d.", pid);
151 1 : return TRACE_SUCCESS;
152 : }
153 :
154 16 : STATIC TraStatus TraceHandleCmd(const void* handle, const TraceDataMsg* msg, uint32_t len)
155 : {
156 16 : if (msg->status == MSG_STATUS_LONG_LINK) {
157 6 : ADIAG_INF("trace long link.");
158 6 : return TraceHandleLinkMsg(handle);
159 : } else {
160 10 : TraStatus ret = TRACE_FAILURE;
161 10 : if ((msg->data[0] == TRACE_HELLO_MSG) && (len >= sizeof(TraceHelloMsg))) {
162 5 : ADIAG_INF("trace hello msg.");
163 5 : ret = TraceHandleHelloMsg(handle, (const TraceHelloMsg*)msg->data);
164 5 : } else if ((msg->data[0] == TRACE_END_MSG) && (len >= sizeof(TraceEndMsg))) {
165 4 : ADIAG_INF("trace end msg.");
166 4 : ret = TraceHandleEndMsg(handle, (const TraceEndMsg*)msg->data);
167 : } else {
168 1 : ADIAG_INF("invalid trace cmd, msgType = %c.", msg->data[0]);
169 1 : ret = TRACE_FAILURE;
170 : }
171 10 : TraceAdxDestroyCommHandle(handle);
172 10 : return ret;
173 : }
174 : }
175 :
176 19 : int32_t TraceDeviceProcess(AdxCommConHandle handle, const void* value, uint32_t len)
177 : {
178 19 : if (TraceAdxIsCommHandleValid(handle) != TRACE_SUCCESS) {
179 1 : ADIAG_ERR("handle is invalid.");
180 1 : return TRACE_FAILURE;
181 : }
182 18 : if ((value == NULL) || (len < sizeof(TraceDataMsg))) {
183 2 : TraceAdxDestroyCommHandle(handle);
184 2 : ADIAG_ERR("value is invalid, len = %u bytes.", len);
185 2 : return TRACE_FAILURE;
186 : }
187 16 : TraStatus ret = TraceHandleCmd(handle, (const TraceDataMsg*)value, len);
188 16 : if (ret != TRACE_SUCCESS) {
189 13 : return TRACE_FAILURE;
190 : }
191 3 : return TRACE_SUCCESS;
192 : }
193 :
194 15 : int32_t TraceDeviceExit(void) { return TRACE_SUCCESS; }
|