Rollback from r3608 to r3606
[public/netxms.git] / src / agent / core / trap.cpp
CommitLineData
5039dede
AK
1/*
2** NetXMS multiplatform core agent
3** Copyright (C) 2003, 2004, 2005, 2006, 2007, 2008 Victor Kirhenshtein
4**
5** This program is free software; you can redistribute it and/or modify
6** it under the terms of the GNU General Public License as published by
7** the Free Software Foundation; either version 2 of the License, or
8** (at your option) any later version.
9**
10** This program is distributed in the hope that it will be useful,
11** but WITHOUT ANY WARRANTY; without even the implied warranty of
12** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13** GNU General Public License for more details.
14**
15** You should have received a copy of the GNU General Public License
16** along with this program; if not, write to the Free Software
17** Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
18**
19** File: trap.cpp
20**
21**/
22
23#include "nxagentd.h"
24#include <stdarg.h>
25
26
27//
28// Static data
29//
30
31static Queue *m_pTrapQueue = NULL;
32
33
34//
35// Trap sender
36//
37
38THREAD_RESULT THREAD_CALL TrapSender(void *pArg)
39{
40 CSCP_MESSAGE *pMsg;
41 DWORD i;
42 BOOL bTrapSent;
43
44 m_pTrapQueue = new Queue;
45 while(1)
46 {
47 pMsg = (CSCP_MESSAGE *)m_pTrapQueue->GetOrBlock();
48 if (pMsg == INVALID_POINTER_VALUE)
49 break;
50
51 bTrapSent = FALSE;
52
53 MutexLock(g_hSessionListAccess, INFINITE);
54 for(i = 0; i < g_dwMaxSessions; i++)
55 if (g_pSessionList[i] != NULL)
56 if (g_pSessionList[i]->AcceptTraps())
57 {
58 g_pSessionList[i]->SendRawMessage(pMsg);
59 bTrapSent = TRUE;
60 }
61 MutexUnlock(g_hSessionListAccess);
62
63 if (bTrapSent)
64 {
65 free(pMsg);
66 }
67 else
68 {
69 m_pTrapQueue->Insert(pMsg); // Re-queue trap
70 ThreadSleep(1);
71 }
72 }
73 delete m_pTrapQueue;
74 m_pTrapQueue = NULL;
75 DebugPrintf(INVALID_INDEX, _T("Trap sender thread terminated"));
76 return THREAD_OK;
77}
78
79
80//
81// Shutdown trap sender
82//
83
84void ShutdownTrapSender()
85{
86 m_pTrapQueue->SetShutdownMode();
87}
88
89
90//
91// Send trap to server
92//
93
94void SendTrap(DWORD dwEventCode, int iNumArgs, TCHAR **ppArgList)
95{
96 int i;
97 CSCPMessage msg;
98
99 msg.SetCode(CMD_TRAP);
100 msg.SetId(0);
101 msg.SetVariable(VID_EVENT_CODE, dwEventCode);
102 msg.SetVariable(VID_NUM_ARGS, (WORD)iNumArgs);
103 for(i = 0; i < iNumArgs; i++)
104 msg.SetVariable(VID_EVENT_ARG_BASE + i, ppArgList[i]);
105 if (m_pTrapQueue != NULL)
106 m_pTrapQueue->Put(msg.CreateMessage());
107}
108
109
110//
111// Send trap - variant 2
112// Arguments:
113// dwEventCode - Event code
114// pszFormat - Parameter format string, each parameter represented by one character.
115// The following format characters can be used:
116// s - String
117// d - Decimal integer
118// x - Hex integer
119// a - IP address
120// i - Object ID
121// D - 64-bit decimal integer
122// X - 64-bit hex integer
123//
124
125void SendTrap(DWORD dwEventCode, const char *pszFormat, va_list args)
126{
127 int i, iNumArgs;
128 TCHAR *ppArgList[64];
129 static TCHAR badFormat[] = _T("BAD FORMAT");
130
131 iNumArgs = (pszFormat == NULL) ? 0 : (int)strlen(pszFormat);
132 for(i = 0; i < iNumArgs; i++)
133 {
134 switch(pszFormat[i])
135 {
136 case 's':
137 ppArgList[i] = va_arg(args, TCHAR *);
138 if (ppArgList[i] == NULL)
139 ppArgList[i] = (TCHAR *)_T("");
140 break;
141 case 'd':
142 ppArgList[i] = (char *)malloc(16);
143 sprintf(ppArgList[i], "%d", va_arg(args, LONG));
144 break;
145 case 'D':
146 ppArgList[i] = (char *)malloc(32);
147 sprintf(ppArgList[i], INT64_FMT, va_arg(args, INT64));
148 break;
149 case 'x':
150 case 'i':
151 ppArgList[i] = (char *)malloc(16);
152 sprintf(ppArgList[i], "0x%08X", va_arg(args, DWORD));
153 break;
154 case 'X':
155 ppArgList[i] = (char *)malloc(32);
156#ifdef _WIN32
157 sprintf(ppArgList[i], "0x%016I64X", va_arg(args, QWORD));
158#else
159 sprintf(ppArgList[i], "0x%016llX", va_arg(args, QWORD));
160#endif
161 break;
162 case 'a':
163 ppArgList[i] = (char *)malloc(16);
164 IpToStr(va_arg(args, DWORD), ppArgList[i]);
165 break;
166 default:
167 ppArgList[i] = badFormat;
168 break;
169 }
170 }
171
172 SendTrap(dwEventCode, iNumArgs, ppArgList);
173
174 for(i = 0; i < iNumArgs; i++)
175 if ((pszFormat[i] == 'd') || (pszFormat[i] == 'x') ||
176 (pszFormat[i] == 'D') || (pszFormat[i] == 'X') ||
177 (pszFormat[i] == 'i') || (pszFormat[i] == 'a'))
178 free(ppArgList[i]);
179}
180
181
182//
183// Send trap - variant 3
184// Same as variant 2, but uses argument list instead of va_list
185//
186
187void SendTrap(DWORD dwEventCode, const char *pszFormat, ...)
188{
189 va_list args;
190
191 va_start(args, pszFormat);
192 SendTrap(dwEventCode, pszFormat, args);
193 va_end(args);
194}