- next iteration of SLM, still half-baked
authorAlex Kalimulin <alex@netxms.org>
Sun, 21 Aug 2011 18:05:49 +0000 (18:05 +0000)
committerAlex Kalimulin <alex@netxms.org>
Sun, 21 Aug 2011 18:05:49 +0000 (18:05 +0000)
src/server/core/bizservice.cpp [new file with mode: 0644]
src/server/core/main.cpp
src/server/core/nodelink.cpp [new file with mode: 0644]
src/server/core/nxcore.vcproj
src/server/core/slm_objects.cpp [deleted file]
src/server/core/slmcheck.cpp [new file with mode: 0644]
src/server/include/nms_objects.h
src/server/include/nxsrvapi.h

diff --git a/src/server/core/bizservice.cpp b/src/server/core/bizservice.cpp
new file mode 100644 (file)
index 0000000..6a2fcec
--- /dev/null
@@ -0,0 +1,243 @@
+/* 
+** NetXMS - Network Management System
+** Copyright (C) 2003-2011 NetXMS Team
+**
+** This program is free software; you can redistribute it and/or modify
+** it under the terms of the GNU General Public License as published by
+** the Free Software Foundation; either version 2 of the License, or
+** (at your option) any later version.
+**
+** This program is distributed in the hope that it will be useful,
+** but WITHOUT ANY WARRANTY; without even the implied warranty of
+** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+** GNU General Public License for more details.
+**
+** You should have received a copy of the GNU General Public License
+** along with this program; if not, write to the Free Software
+** Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+**
+** File: bizservice.cpp
+**
+**/
+
+#include "nxcore.h"
+#include "nms_objects.h"
+
+#define QUERY_LENGTH           (512)
+
+//
+// Service default constructor
+//
+
+BizService::BizService()
+     :Container()
+{
+       m_busy = FALSE;
+       _tcscpy(m_szName, _T("Default"));
+}
+
+
+//
+// Constructor for new service object
+//
+
+BizService::BizService(const TCHAR *name)
+     :Container(name, 0)
+{
+       m_dwId = 0;
+       m_busy = false;
+       nx_strncpy(m_szName, name, MAX_OBJECT_NAME);
+}
+
+
+//
+// Service class destructor
+//
+
+BizService::~BizService()
+{
+}
+
+void BizService::calculateCompoundStatus(BOOL bForcedRecalc /*= FALSE*/)
+{
+       int i, iCount, iMostCriticalStatus;
+
+       LockChildList(FALSE);
+
+       for(i = 0, iCount = 0, iMostCriticalStatus = -1; i < int(m_dwChildCount); i++)
+       {
+               int iChildStatus = m_pChildList[i]->PropagatedStatus();
+               if ((iChildStatus < STATUS_UNKNOWN) &&
+                       (iChildStatus > iMostCriticalStatus))
+               {
+                       iMostCriticalStatus = iChildStatus;
+                       iCount++;
+               }
+       }
+       m_iStatus = (iCount > 0) ? iMostCriticalStatus : STATUS_UNKNOWN;
+
+       UnlockChildList();
+}
+
+//
+// Create object from database data
+//
+
+BOOL BizService::CreateFromDB(DWORD id)
+{
+       m_dwId = id;
+
+       if (!loadCommonProperties())
+               return FALSE;
+
+       // now it doesn't make any sense but hopefully will do in the future
+       DB_STATEMENT hStmt = DBPrepare(g_hCoreDB, _T("SELECT service_id FROM business_services WHERE service_id=?"));
+       if (hStmt == NULL)
+       {
+               DbgPrintf(4, _T("Cannot prepare select from business_services"));
+               return FALSE;
+       }
+       DBBind(hStmt, 1, DB_SQLTYPE_INTEGER, m_dwId);
+       DB_RESULT hResult = DBSelectPrepared(hStmt);
+       if (hResult == NULL)
+       {
+               DBFreeStatement(hStmt);
+               return FALSE;
+       }
+
+       if (DBGetNumRows(hResult) == 0)
+       {
+               DBFreeResult(hResult);
+               DBFreeStatement(hStmt);
+               DbgPrintf(4, _T("Cannot load biz service object %ld - record missing"), (long)m_dwId);
+               return FALSE;
+       }
+
+       // m_svcStatus  = DBGetFieldULong(hResult, 0, 0);
+
+       DBFreeResult(hResult);
+       DBFreeStatement(hStmt);
+
+       // Load access list
+       loadACLFromDB();
+
+       return TRUE;
+}
+
+
+//
+// Save service to database
+//
+
+BOOL BizService::SaveToDB(DB_HANDLE hdb)
+{
+       BOOL bNewObject = TRUE;
+
+       LockData();
+
+       saveCommonProperties(hdb);
+   
+       DB_STATEMENT hStmt = DBPrepare(hdb, _T("SELECT service_id FROM business_services WHERE service_id=?"));
+       if (hStmt == NULL)
+               return FALSE;
+       DBBind(hStmt, 0, DB_SQLTYPE_INTEGER, m_dwId);
+       DB_RESULT hResult = DBSelectPrepared(hStmt);
+       if (hResult != NULL)
+       {
+               bNewObject = (DBGetNumRows(hResult) <= 0);
+               DBFreeResult(hResult);
+       }
+       DBFreeStatement(hStmt);
+
+       hStmt = DBPrepare(g_hCoreDB, bNewObject ? _T("INSERT INTO business_services (service_id) VALUES (?)") :
+                                                                                         _T("UPDATE business_services SET service_id=service_id WHERE service_id=?"));
+       if (hStmt == NULL)      
+               return FALSE;
+       DBBind(hStmt, 1, DB_SQLTYPE_INTEGER, m_dwId);
+       if (!DBExecute(hStmt))
+       {
+               DBFreeStatement(hStmt);
+               return FALSE;
+       }
+
+       DBFreeResult(hResult);
+       DBFreeStatement(hStmt);
+
+       saveACLToDB(hdb);
+
+       // Unlock object and clear modification flag
+       m_bIsModified = FALSE;
+       UnlockData();
+       return TRUE;
+}
+
+
+//
+// Delete object from database
+//
+
+BOOL BizService::DeleteFromDB()
+{
+   TCHAR szQuery[QUERY_LENGTH];
+   BOOL bSuccess;
+
+   bSuccess = NetObj::DeleteFromDB();
+   if (bSuccess)
+   {
+      _sntprintf(szQuery, QUERY_LENGTH, _T("DELETE FROM business_services WHERE id=%d"), m_dwId);
+      QueueSQLRequest(szQuery);
+   }
+
+   return bSuccess;
+}
+
+
+//
+// Create CSCP message with object's data
+//
+
+void BizService::CreateMessage(CSCPMessage *pMsg)
+{
+   NetObj::CreateMessage(pMsg);
+   // pMsg->SetVariable(VID_ID, m_dwId);
+   // pMsg->SetVariable(VID_STATUS, m_svcStatus);
+}
+
+
+//
+// Modify object from message
+//
+
+DWORD BizService::ModifyFromMessage(CSCPMessage *pRequest, BOOL bAlreadyLocked)
+{
+   if (!bAlreadyLocked)
+      LockData();
+
+       // if (pRequest->IsVariableExist(VID_STATUS))
+       //      m_svcStatus = pRequest->GetVariableLong(VID_STATUS);
+
+   return NetObj::ModifyFromMessage(pRequest, TRUE);
+}
+
+//
+// A callback for poller
+//
+
+void BizService::poll( ClientSession *pSession, DWORD dwRqId, int nPoller )
+{
+       for (int i = 0; i < int(m_dwChildCount); i++)
+       {
+               if (m_pChildList[i]->Type() == OBJECT_SLMCHECK)
+                       ((SlmCheck*)m_pChildList[i])->execute();
+       }
+
+       LockParentList(FALSE);
+       for(int i = 0; i < int(m_dwParentCount); i++)
+               m_pParentList[i]->calculateCompoundStatus();
+       UnlockParentList();
+
+       m_busy = false;
+}
+
+
+
index cbea338..befa060 100644 (file)
@@ -121,7 +121,6 @@ DWORD g_dwTopologyPollingInterval;
 DWORD g_dwConditionPollingInterval;
 DWORD g_dwPingSize;
 DWORD g_dwAuditFlags;
-DWORD g_dwSlmFlags;
 TCHAR g_szDataDir[MAX_PATH] = _T("");
 TCHAR g_szLibDir[MAX_PATH] = DEFAULT_LIBDIR;
 int g_nDBSyntax = DB_SYNTAX_UNKNOWN;
@@ -313,7 +312,7 @@ static void LoadGlobalConfig()
                g_dwFlags |= AF_CHECK_TRUSTED_NODES;
 
        if (ConfigReadInt(_T("EnableSlm"), 1))
-               g_dwSlmFlags |= SLM_ENABLED;
+               g_dwFlags |= AF_ENABLE_SLM;
        
        if (g_szDataDir[0] == 0)
        {
@@ -740,8 +739,6 @@ retry_db_lock:
        ThreadCreate(WatchdogThread, 0, NULL);
        ThreadCreate(NodePoller, 0, NULL);
        ThreadCreate(JobManagerThread, 0, NULL);
-       if (g_dwSlmFlags & SLM_ENABLED)
-               ThreadCreate(ServiceLevelMonitoring, 0, NULL);
        m_thSyncer = ThreadCreateEx(Syncer, 0, NULL);
        m_thHouseKeeper = ThreadCreateEx(HouseKeeper, 0, NULL);
        m_thPollManager = ThreadCreateEx(PollManager, 0, NULL);
diff --git a/src/server/core/nodelink.cpp b/src/server/core/nodelink.cpp
new file mode 100644 (file)
index 0000000..358cd52
--- /dev/null
@@ -0,0 +1,221 @@
+/* 
+** NetXMS - Network Management System
+** Copyright (C) 2003-2011 NetXMS Team
+**
+** This program is free software; you can redistribute it and/or modify
+** it under the terms of the GNU General Public License as published by
+** the Free Software Foundation; either version 2 of the License, or
+** (at your option) any later version.
+**
+** This program is distributed in the hope that it will be useful,
+** but WITHOUT ANY WARRANTY; without even the implied warranty of
+** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+** GNU General Public License for more details.
+**
+** You should have received a copy of the GNU General Public License
+** along with this program; if not, write to the Free Software
+** Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+**
+** File: nodelink.cpp
+**
+**/
+
+#include "nxcore.h"
+#include "nms_objects.h"
+
+#define QUERY_LENGTH           (512)
+
+//
+// NodeLink default constructor
+//
+
+NodeLink::NodeLink()
+:NetObj()
+{
+       _tcscpy(m_szName, _T("Default"));
+}
+
+
+//
+// Constructor for new nodelink object
+//
+
+NodeLink::NodeLink(const TCHAR *name)
+:NetObj()
+{
+       nx_strncpy(m_szName, name, MAX_OBJECT_NAME);
+}
+
+
+//
+// Nodelink class destructor
+//
+
+NodeLink::~NodeLink()
+{
+       safe_delete_and_null(m_node);
+}
+
+void NodeLink::calculateCompoundStatus(BOOL bForcedRecalc /*= FALSE*/)
+{
+       m_iStatus = STATUS_NORMAL;
+}
+
+//
+// Create object from database data
+//
+
+BOOL NodeLink::CreateFromDB(DWORD id)
+{
+       const int script_length = 1024;
+       DWORD nodeId;
+       m_dwId = id;
+
+       if (!loadCommonProperties())
+               return FALSE;
+
+       DB_STATEMENT hStmt = DBPrepare(g_hCoreDB, _T("SELECT node_id FROM node_links WHERE nodelink_id=?"));
+       if (hStmt == NULL)
+       {
+               DbgPrintf(4, _T("Cannot prepare select from node_links"));
+               return FALSE;
+       }
+       DBBind(hStmt, 1, DB_SQLTYPE_INTEGER, m_dwId);
+
+       DB_RESULT hResult = DBSelectPrepared(hStmt);
+       if (hResult == NULL)
+       {
+               DBFreeStatement(hStmt);
+               return FALSE;
+       }
+
+       if (DBGetNumRows(hResult) == 0)
+       {
+               DBFreeResult(hResult);
+               DBFreeStatement(hStmt);
+               DbgPrintf(4, _T("Cannot load nodelink object %ld - record missing"), (long)m_dwId);
+               return FALSE;
+       }
+
+       nodeId  = DBGetFieldLong(hResult, 0, 0);
+       if (nodeId > 0)
+       {
+               m_node = new Node;
+               m_node->CreateFromDB(nodeId);
+       }
+
+       DBFreeResult(hResult);
+       DBFreeStatement(hStmt);
+
+       // Load access list
+       loadACLFromDB();
+
+       return TRUE;
+}
+
+
+//
+// Save service to database
+//
+
+BOOL NodeLink::SaveToDB(DB_HANDLE hdb)
+{
+       BOOL bNewObject = TRUE;
+       TCHAR szQuery[QUERY_LENGTH];
+
+       LockData();
+
+       saveCommonProperties(hdb);
+
+       DB_STATEMENT hStmt = DBPrepare(hdb, _T("SELECT nodelink_id FROM node_links WHERE nodelink_id=?"));
+       if (hStmt == NULL)
+       {
+               DbgPrintf(4, _T("Cannot prepare select from node_links"));
+               return FALSE;
+       }
+       DBBind(hStmt, 0, DB_SQLTYPE_INTEGER, m_dwId);
+       DB_RESULT hResult = DBSelectPrepared(hStmt);
+       if (hResult != NULL)
+       {
+               bNewObject = (DBGetNumRows(hResult) <= 0);
+               DBFreeResult(hResult);
+       }
+       DBFreeStatement(hStmt);
+
+       if (bNewObject)
+               nx_strncpy(szQuery, _T("INSERT INTO node_links (node_id, nodelink_id) VALUES (?, ?)"), QUERY_LENGTH);
+       else
+               nx_strncpy(szQuery, _T("UPDATE node_links SET node_id=? WHERE nodelink_id=?"), QUERY_LENGTH);
+       hStmt = DBPrepare(g_hCoreDB, szQuery);
+       if (hStmt == NULL)      
+       {
+               DbgPrintf(4, _T("Cannot prepare %s from node_links"), bNewObject ? _T("insert") : _T("update"));
+               return FALSE;
+       }
+       DBBind(hStmt, 1, DB_SQLTYPE_INTEGER, m_node == NULL ? 0 : m_node->Id());
+       DBBind(hStmt, 2, DB_SQLTYPE_INTEGER, m_dwId);
+       if (!DBExecute(hStmt))
+       {
+               DbgPrintf(4, _T("Cannot execute %s on node_links"), bNewObject ? _T("insert") : _T("update"));
+               DBFreeStatement(hStmt);
+               return FALSE;
+       }
+
+       DBFreeResult(hResult);
+       DBFreeStatement(hStmt);
+
+       saveACLToDB(hdb);
+
+       // Unlock object and clear modification flag
+       m_bIsModified = FALSE;
+       UnlockData();
+       return TRUE;
+}
+
+
+//
+// Delete object from database
+//
+
+BOOL NodeLink::DeleteFromDB()
+{
+       TCHAR szQuery[QUERY_LENGTH];
+       BOOL bSuccess;
+
+       bSuccess = NetObj::DeleteFromDB();
+       if (bSuccess)
+       {
+               _sntprintf(szQuery, QUERY_LENGTH, _T("DELETE FROM node_links WHERE nodelink_id=%d"), m_dwId);
+               QueueSQLRequest(szQuery);
+       }
+
+       return bSuccess;
+}
+
+
+//
+// Create CSCP message with object's data
+//
+
+void NodeLink::CreateMessage(CSCPMessage *pMsg)
+{
+       NetObj::CreateMessage(pMsg);
+       // pMsg->SetVariable(VID_ID, m_dwId);
+       // pMsg->SetVariable(VID_STATUS, m_svcStatus);
+}
+
+
+//
+// Modify object from message
+//
+
+DWORD NodeLink::ModifyFromMessage(CSCPMessage *pRequest, BOOL bAlreadyLocked)
+{
+       if (!bAlreadyLocked)
+               LockData();
+
+       // if (pRequest->IsVariableExist(VID_STATUS))
+       //      m_svcStatus = pRequest->GetVariableLong(VID_STATUS);
+
+       return NetObj::ModifyFromMessage(pRequest, TRUE);
+}
index 15e8695..2453f1d 100644 (file)
                                RelativePath=".\beacon.cpp"\r
                                >\r
                        </File>\r
+                       <File\r
+                               RelativePath=".\bizservice.cpp"\r
+                               >\r
+                       </File>\r
                        <File\r
                                RelativePath=".\bridge.cpp"\r
                                >\r
                                RelativePath=".\node.cpp"\r
                                >\r
                        </File>\r
+                       <File\r
+                               RelativePath=".\nodelink.cpp"\r
+                               >\r
+                       </File>\r
                        <File\r
                                RelativePath=".\np.cpp"\r
                                >\r
                                >\r
                        </File>\r
                        <File\r
-                               RelativePath=".\slm_objects.cpp"\r
+                               RelativePath=".\slmcheck.cpp"\r
                                >\r
                        </File>\r
                        <File\r
diff --git a/src/server/core/slm_objects.cpp b/src/server/core/slm_objects.cpp
deleted file mode 100644 (file)
index 5e78366..0000000
+++ /dev/null
@@ -1,586 +0,0 @@
-/* 
-** NetXMS - Network Management System
-** Copyright (C) 2003-2011 NetXMS Team
-**
-** This program is free software; you can redistribute it and/or modify
-** it under the terms of the GNU General Public License as published by
-** the Free Software Foundation; either version 2 of the License, or
-** (at your option) any later version.
-**
-** This program is distributed in the hope that it will be useful,
-** but WITHOUT ANY WARRANTY; without even the implied warranty of
-** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-** GNU General Public License for more details.
-**
-** You should have received a copy of the GNU General Public License
-** along with this program; if not, write to the Free Software
-** Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
-**
-** File: slm_objects.cpp
-**
-**/
-
-#include "nxcore.h"
-#include "nms_objects.h"
-
-#define QUERY_LENGTH           (512)
-
-//
-// Service default constructor
-//
-
-BizService::BizService()
-     :Container()
-{
-       _tcscpy(m_szName, _T("Default"));
-}
-
-
-//
-// Constructor for new service object
-//
-
-BizService::BizService(const TCHAR *name)
-     :Container(name, 0)
-{
-       m_dwId = 0;
-       nx_strncpy(m_szName, name, MAX_OBJECT_NAME);
-}
-
-
-//
-// Service class destructor
-//
-
-BizService::~BizService()
-{
-}
-
-void BizService::calculateCompoundStatus(BOOL bForcedRecalc /*= FALSE*/)
-{
-       int i, iCount, iMostCriticalStatus;
-
-       LockChildList(FALSE);
-
-       for(i = 0, iCount = 0, iMostCriticalStatus = -1; i < m_dwChildCount; i++)
-       {
-               int iChildStatus = m_pChildList[i]->PropagatedStatus();
-               if ((iChildStatus < STATUS_UNKNOWN) &&
-                       (iChildStatus > iMostCriticalStatus))
-               {
-                       iMostCriticalStatus = iChildStatus;
-                       iCount++;
-               }
-       }
-       m_iStatus = (iCount > 0) ? iMostCriticalStatus : STATUS_UNKNOWN;
-
-       UnlockChildList();
-}
-
-//
-// Create object from database data
-//
-
-BOOL BizService::CreateFromDB(DWORD id)
-{
-       m_dwId = id;
-
-       if (!loadCommonProperties())
-               return FALSE;
-
-       // now it doesn't make any sense but hopefully will do in the future
-       DB_STATEMENT hStmt = DBPrepare(g_hCoreDB, _T("SELECT service_id FROM business_services WHERE service_id=?"));
-       if (hStmt == NULL)
-       {
-               DbgPrintf(4, _T("Cannot prepare select from business_services"));
-               return FALSE;
-       }
-       DBBind(hStmt, 1, DB_SQLTYPE_INTEGER, m_dwId);
-       DB_RESULT hResult = DBSelectPrepared(hStmt);
-       if (hResult == NULL)
-       {
-               DBFreeStatement(hStmt);
-               return FALSE;
-       }
-
-       if (DBGetNumRows(hResult) == 0)
-       {
-               DBFreeResult(hResult);
-               DBFreeStatement(hStmt);
-               DbgPrintf(4, _T("Cannot load biz service object %ld - record missing"), (long)m_dwId);
-               return FALSE;
-       }
-
-       // m_svcStatus  = DBGetFieldULong(hResult, 0, 0);
-
-       DBFreeResult(hResult);
-       DBFreeStatement(hStmt);
-
-       // Load access list
-       loadACLFromDB();
-
-       return TRUE;
-}
-
-
-//
-// Save service to database
-//
-
-BOOL BizService::SaveToDB(DB_HANDLE hdb)
-{
-       BOOL bNewObject = TRUE;
-       TCHAR szQuery[QUERY_LENGTH];
-
-       LockData();
-
-       saveCommonProperties(hdb);
-   
-       DB_STATEMENT hStmt = DBPrepare(hdb, _T("SELECT service_id FROM business_services WHERE service_id=?"));
-       if (hStmt == NULL)
-       {
-               DbgPrintf(4, _T("Cannot prepare select from business_services"));
-               return FALSE;
-       }
-       DBBind(hStmt, 0, DB_SQLTYPE_INTEGER, m_dwId);
-       DB_RESULT hResult = DBSelectPrepared(hStmt);
-       if (hResult != NULL)
-       {
-               bNewObject = (DBGetNumRows(hResult) <= 0);
-               DBFreeResult(hResult);
-       }
-       DBFreeStatement(hStmt);
-
-       if (bNewObject)
-               nx_strncpy(szQuery, _T("INSERT INTO business_services (service_id) VALUES (?)"), QUERY_LENGTH);
-       else
-               nx_strncpy(szQuery, _T("UPDATE business_services SET service_id=service_id WHERE service_id=?"), QUERY_LENGTH);
-       hStmt = DBPrepare(g_hCoreDB, szQuery);
-       if (hStmt == NULL)      
-       {
-               DbgPrintf(4, _T("Cannot prepare %s from business_services"), bNewObject ? _T("insert") : _T("update"));
-               return FALSE;
-       }
-       DBBind(hStmt, 1, DB_SQLTYPE_INTEGER, m_dwId);
-       if (!DBExecute(hStmt))
-       {
-               DbgPrintf(4, _T("Cannot execute %s on business_services"), bNewObject ? _T("insert") : _T("update"));
-               DBFreeStatement(hStmt);
-               return FALSE;
-       }
-
-       DBFreeResult(hResult);
-       DBFreeStatement(hStmt);
-
-       saveACLToDB(hdb);
-
-       // Unlock object and clear modification flag
-       m_bIsModified = FALSE;
-       UnlockData();
-       return TRUE;
-}
-
-
-//
-// Delete object from database
-//
-
-BOOL BizService::DeleteFromDB()
-{
-   TCHAR szQuery[QUERY_LENGTH];
-   BOOL bSuccess;
-
-   bSuccess = NetObj::DeleteFromDB();
-   if (bSuccess)
-   {
-      _sntprintf(szQuery, QUERY_LENGTH, _T("DELETE FROM business_services WHERE id=%d"), m_dwId);
-      QueueSQLRequest(szQuery);
-   }
-
-   return bSuccess;
-}
-
-
-//
-// Create CSCP message with object's data
-//
-
-void BizService::CreateMessage(CSCPMessage *pMsg)
-{
-   NetObj::CreateMessage(pMsg);
-   // pMsg->SetVariable(VID_ID, m_dwId);
-   // pMsg->SetVariable(VID_STATUS, m_svcStatus);
-}
-
-
-//
-// Modify object from message
-//
-
-DWORD BizService::ModifyFromMessage(CSCPMessage *pRequest, BOOL bAlreadyLocked)
-{
-   if (!bAlreadyLocked)
-      LockData();
-
-       // if (pRequest->IsVariableExist(VID_STATUS))
-       //      m_svcStatus = pRequest->GetVariableLong(VID_STATUS);
-
-   return NetObj::ModifyFromMessage(pRequest, TRUE);
-}
-
-
-
-//
-// SLMCheck default constructor
-//
-
-SlmCheck::SlmCheck()
-:NetObj()
-{
-       _tcscpy(m_szName, _T("Default"));
-       m_state = FALSE;
-       m_script = NULL;
-       m_threshold = NULL;
-       m_reason[0] = _T('\0');
-}
-
-
-//
-// Constructor for new check object
-//
-
-SlmCheck::SlmCheck(const TCHAR *name)
-:NetObj()
-{
-       nx_strncpy(m_szName, name, MAX_OBJECT_NAME);
-       m_state = FALSE;
-       m_script = NULL;
-       m_threshold = NULL;
-       m_reason[0] = _T('\0');
-}
-
-
-//
-// Service class destructor
-//
-
-SlmCheck::~SlmCheck()
-{
-       safe_delete_and_null(m_threshold);
-       safe_free_and_null(m_script);
-}
-
-void SlmCheck::calculateCompoundStatus(BOOL bForcedRecalc /*= FALSE*/)
-{
-       m_iStatus = STATUS_NORMAL;
-}
-
-//
-// Create object from database data
-//
-
-BOOL SlmCheck::CreateFromDB(DWORD id)
-{
-       const int script_length = 1024;
-       DWORD thresholdId;
-       m_dwId = id;
-
-       if (!loadCommonProperties())
-               return FALSE;
-
-       DB_STATEMENT hStmt = DBPrepare(g_hCoreDB, _T("SELECT type,content,threshold_id,state,reason FROM slm_checks WHERE check_id=?"));
-       if (hStmt == NULL)
-       {
-               DbgPrintf(4, _T("Cannot prepare select from slm_checks"));
-               return FALSE;
-       }
-       DBBind(hStmt, 1, DB_SQLTYPE_INTEGER, m_dwId);
-
-       DB_RESULT hResult = DBSelectPrepared(hStmt);
-       if (hResult == NULL)
-       {
-               DBFreeStatement(hStmt);
-               return FALSE;
-       }
-
-       if (DBGetNumRows(hResult) == 0)
-       {
-               DBFreeResult(hResult);
-               DBFreeStatement(hStmt);
-               DbgPrintf(4, _T("Cannot load check object %ld - record missing"), (long)m_dwId);
-               return FALSE;
-       }
-
-       m_type          = SlmCheck::CheckType(DBGetFieldLong(hResult, 0, 0));
-       DBGetField(hResult, 0, 1, m_script, script_length);
-       thresholdId = DBGetFieldLong(hResult, 0, 2);
-       m_state         = DBGetFieldLong(hResult, 0, 3);
-       DBGetField(hResult, 0, 4, m_reason, 255);
-
-       if (thresholdId > 0)
-       {
-               // FIXME: load threshold
-       }
-
-       DBFreeResult(hResult);
-       DBFreeStatement(hStmt);
-
-       // Load access list
-       loadACLFromDB();
-
-       return TRUE;
-}
-
-
-//
-// Save service to database
-//
-
-BOOL SlmCheck::SaveToDB(DB_HANDLE hdb)
-{
-       return TRUE;
-}
-
-
-//
-// Delete object from database
-//
-
-BOOL SlmCheck::DeleteFromDB()
-{
-       TCHAR szQuery[QUERY_LENGTH];
-       BOOL bSuccess;
-
-       bSuccess = NetObj::DeleteFromDB();
-       if (bSuccess)
-       {
-               _sntprintf(szQuery, QUERY_LENGTH, _T("DELETE FROM slm_checks WHERE check_id=%d"), m_dwId);
-               QueueSQLRequest(szQuery);
-       }
-
-       return bSuccess;
-}
-
-
-//
-// Create CSCP message with object's data
-//
-
-void SlmCheck::CreateMessage(CSCPMessage *pMsg)
-{
-       NetObj::CreateMessage(pMsg);
-       // pMsg->SetVariable(VID_ID, m_dwId);
-       // pMsg->SetVariable(VID_STATUS, m_svcStatus);
-}
-
-
-//
-// Modify object from message
-//
-
-DWORD SlmCheck::ModifyFromMessage(CSCPMessage *pRequest, BOOL bAlreadyLocked)
-{
-       if (!bAlreadyLocked)
-               LockData();
-
-       // if (pRequest->IsVariableExist(VID_STATUS))
-       //      m_svcStatus = pRequest->GetVariableLong(VID_STATUS);
-
-       return NetObj::ModifyFromMessage(pRequest, TRUE);
-}
-
-
-//
-// NodeLink default constructor
-//
-
-NodeLink::NodeLink()
-:NetObj()
-{
-       _tcscpy(m_szName, _T("Default"));
-}
-
-
-//
-// Constructor for new nodelink object
-//
-
-NodeLink::NodeLink(const TCHAR *name)
-:NetObj()
-{
-       nx_strncpy(m_szName, name, MAX_OBJECT_NAME);
-}
-
-
-//
-// Nodelink class destructor
-//
-
-NodeLink::~NodeLink()
-{
-       safe_delete_and_null(m_node);
-}
-
-void NodeLink::calculateCompoundStatus(BOOL bForcedRecalc /*= FALSE*/)
-{
-       m_iStatus = STATUS_NORMAL;
-}
-
-//
-// Create object from database data
-//
-
-BOOL NodeLink::CreateFromDB(DWORD id)
-{
-       const int script_length = 1024;
-       DWORD nodeId;
-       m_dwId = id;
-
-       if (!loadCommonProperties())
-               return FALSE;
-
-       DB_STATEMENT hStmt = DBPrepare(g_hCoreDB, _T("SELECT node_id FROM node_links WHERE nodelink_id=?"));
-       if (hStmt == NULL)
-       {
-               DbgPrintf(4, _T("Cannot prepare select from node_links"));
-               return FALSE;
-       }
-       DBBind(hStmt, 1, DB_SQLTYPE_INTEGER, m_dwId);
-
-       DB_RESULT hResult = DBSelectPrepared(hStmt);
-       if (hResult == NULL)
-       {
-               DBFreeStatement(hStmt);
-               return FALSE;
-       }
-
-       if (DBGetNumRows(hResult) == 0)
-       {
-               DBFreeResult(hResult);
-               DBFreeStatement(hStmt);
-               DbgPrintf(4, _T("Cannot load nodelink object %ld - record missing"), (long)m_dwId);
-               return FALSE;
-       }
-
-       nodeId  = DBGetFieldLong(hResult, 0, 0);
-       if (nodeId > 0)
-       {
-               m_node = new Node;
-               m_node->CreateFromDB(nodeId);
-       }
-
-       DBFreeResult(hResult);
-       DBFreeStatement(hStmt);
-
-       // Load access list
-       loadACLFromDB();
-
-       return TRUE;
-}
-
-
-//
-// Save service to database
-//
-
-BOOL NodeLink::SaveToDB(DB_HANDLE hdb)
-{
-       BOOL bNewObject = TRUE;
-       TCHAR szQuery[QUERY_LENGTH];
-
-       LockData();
-
-       saveCommonProperties(hdb);
-
-       DB_STATEMENT hStmt = DBPrepare(hdb, _T("SELECT nodelink_id FROM node_links WHERE nodelink_id=?"));
-       if (hStmt == NULL)
-       {
-               DbgPrintf(4, _T("Cannot prepare select from node_links"));
-               return FALSE;
-       }
-       DBBind(hStmt, 0, DB_SQLTYPE_INTEGER, m_dwId);
-       DB_RESULT hResult = DBSelectPrepared(hStmt);
-       if (hResult != NULL)
-       {
-               bNewObject = (DBGetNumRows(hResult) <= 0);
-               DBFreeResult(hResult);
-       }
-       DBFreeStatement(hStmt);
-
-       if (bNewObject)
-               nx_strncpy(szQuery, _T("INSERT INTO node_links (node_id, nodelink_id) VALUES (?, ?)"), QUERY_LENGTH);
-       else
-               nx_strncpy(szQuery, _T("UPDATE node_links SET node_id=? WHERE nodelink_id=?"), QUERY_LENGTH);
-       hStmt = DBPrepare(g_hCoreDB, szQuery);
-       if (hStmt == NULL)      
-       {
-               DbgPrintf(4, _T("Cannot prepare %s from node_links"), bNewObject ? _T("insert") : _T("update"));
-               return FALSE;
-       }
-       DBBind(hStmt, 1, DB_SQLTYPE_INTEGER, m_node == NULL ? 0 : m_node->Id());
-       DBBind(hStmt, 2, DB_SQLTYPE_INTEGER, m_dwId);
-       if (!DBExecute(hStmt))
-       {
-               DbgPrintf(4, _T("Cannot execute %s on node_links"), bNewObject ? _T("insert") : _T("update"));
-               DBFreeStatement(hStmt);
-               return FALSE;
-       }
-
-       DBFreeResult(hResult);
-       DBFreeStatement(hStmt);
-
-       saveACLToDB(hdb);
-
-       // Unlock object and clear modification flag
-       m_bIsModified = FALSE;
-       UnlockData();
-       return TRUE;
-}
-
-
-//
-// Delete object from database
-//
-
-BOOL NodeLink::DeleteFromDB()
-{
-       TCHAR szQuery[QUERY_LENGTH];
-       BOOL bSuccess;
-
-       bSuccess = NetObj::DeleteFromDB();
-       if (bSuccess)
-       {
-               _sntprintf(szQuery, QUERY_LENGTH, _T("DELETE FROM node_links WHERE nodelink_id=%d"), m_dwId);
-               QueueSQLRequest(szQuery);
-       }
-
-       return bSuccess;
-}
-
-
-//
-// Create CSCP message with object's data
-//
-
-void NodeLink::CreateMessage(CSCPMessage *pMsg)
-{
-       NetObj::CreateMessage(pMsg);
-       // pMsg->SetVariable(VID_ID, m_dwId);
-       // pMsg->SetVariable(VID_STATUS, m_svcStatus);
-}
-
-
-//
-// Modify object from message
-//
-
-DWORD NodeLink::ModifyFromMessage(CSCPMessage *pRequest, BOOL bAlreadyLocked)
-{
-       if (!bAlreadyLocked)
-               LockData();
-
-       // if (pRequest->IsVariableExist(VID_STATUS))
-       //      m_svcStatus = pRequest->GetVariableLong(VID_STATUS);
-
-       return NetObj::ModifyFromMessage(pRequest, TRUE);
-}
diff --git a/src/server/core/slmcheck.cpp b/src/server/core/slmcheck.cpp
new file mode 100644 (file)
index 0000000..615f31d
--- /dev/null
@@ -0,0 +1,287 @@
+/* 
+** NetXMS - Network Management System
+** Copyright (C) 2003-2011 NetXMS Team
+**
+** This program is free software; you can redistribute it and/or modify
+** it under the terms of the GNU General Public License as published by
+** the Free Software Foundation; either version 2 of the License, or
+** (at your option) any later version.
+**
+** This program is distributed in the hope that it will be useful,
+** but WITHOUT ANY WARRANTY; without even the implied warranty of
+** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+** GNU General Public License for more details.
+**
+** You should have received a copy of the GNU General Public License
+** along with this program; if not, write to the Free Software
+** Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+**
+** File: slmcheck.cpp
+**
+**/
+
+#include "nxcore.h"
+#include "nms_objects.h"
+
+#define QUERY_LENGTH           (512)
+
+//
+// SLM check default constructor
+//
+
+SlmCheck::SlmCheck()
+:NetObj()
+{
+       _tcscpy(m_szName, _T("Default"));
+       m_state = FALSE;
+       m_script = NULL;
+       m_threshold = NULL;
+       m_reason[0] = _T('\0');
+}
+
+
+//
+// Constructor for new check object
+//
+
+SlmCheck::SlmCheck(const TCHAR *name)
+:NetObj()
+{
+       nx_strncpy(m_szName, name, MAX_OBJECT_NAME);
+       m_state = FALSE;
+       m_script = NULL;
+       m_threshold = NULL;
+       m_reason[0] = _T('\0');
+}
+
+
+//
+// Service class destructor
+//
+
+SlmCheck::~SlmCheck()
+{
+       safe_delete_and_null(m_threshold);
+       safe_free_and_null(m_script);
+}
+
+void SlmCheck::calculateCompoundStatus(BOOL bForcedRecalc /*= FALSE*/)
+{
+       /*
+       if (m_script == NULL && m_threshold == NULL)
+               m_iStatus = STATUS_UNKNOWN;
+       else
+               m_iStatus = STATUS_NORMAL;
+       */
+}
+
+//
+// Create object from database data
+//
+
+BOOL SlmCheck::CreateFromDB(DWORD id)
+{
+       const int script_length = 1024;
+       DWORD thresholdId;
+       const int errorMsgLen = 512;
+       TCHAR errorMsg[errorMsgLen];
+
+       m_dwId = id;
+
+       if (!loadCommonProperties())
+               return FALSE;
+
+       DB_STATEMENT hStmt = DBPrepare(g_hCoreDB, _T("SELECT type,content,threshold_id,state,reason FROM slm_checks WHERE check_id=?"));
+       if (hStmt == NULL)
+       {
+               DbgPrintf(4, _T("Cannot prepare select from slm_checks"));
+               return FALSE;
+       }
+       DBBind(hStmt, 1, DB_SQLTYPE_INTEGER, m_dwId);
+
+       DB_RESULT hResult = DBSelectPrepared(hStmt);
+       if (hResult == NULL)
+       {
+               DBFreeStatement(hStmt);
+               return FALSE;
+       }
+
+       if (DBGetNumRows(hResult) == 0)
+       {
+               DBFreeResult(hResult);
+               DBFreeStatement(hStmt);
+               DbgPrintf(4, _T("Cannot load check object %ld - record missing"), (long)m_dwId);
+               return FALSE;
+       }
+
+       m_type          = SlmCheck::CheckType(DBGetFieldLong(hResult, 0, 0));
+       m_script = DBGetField(hResult, 0, 1, NULL, script_length);
+       thresholdId = DBGetFieldLong(hResult, 0, 2);
+       m_state         = DBGetFieldLong(hResult, 0, 3);
+       DBGetField(hResult, 0, 4, m_reason, 255);
+
+       if (thresholdId > 0)
+       {
+               // FIXME: load threshold
+       }
+
+       // Compile script if there is one
+       if (m_type == check_script && m_script != NULL)
+       {
+               m_pCompiledScript = (NXSL_Program*)NXSLCompile(m_script, errorMsg, errorMsgLen);
+               if (m_pCompiledScript == NULL)
+               {
+                       DbgPrintf(2, _T("Check %s/%ld script compilation failed - %s"), 
+                               m_szName, (long)m_dwId, errorMsg); 
+               }
+       }
+
+       DBFreeResult(hResult);
+       DBFreeStatement(hStmt);
+
+       // Load access list
+       loadACLFromDB();
+
+       return TRUE;
+}
+
+
+//
+// Save service to database
+//
+
+BOOL SlmCheck::SaveToDB(DB_HANDLE hdb)
+{
+       BOOL bNewObject = TRUE;
+       BOOL ret = FALSE;
+
+       LockData();
+
+       saveCommonProperties(hdb);
+   
+       DB_STATEMENT hStmt = DBPrepare(hdb, _T("SELECT check_id FROM slm_checks WHERE check_id=?"));
+       if (hStmt == NULL)
+               goto finish;
+       DBBind(hStmt, 0, DB_SQLTYPE_INTEGER, m_dwId);
+       DB_RESULT hResult = DBSelectPrepared(hStmt);
+       if (hResult != NULL)
+       {
+               bNewObject = (DBGetNumRows(hResult) <= 0);
+               DBFreeResult(hResult);
+       }
+       DBFreeStatement(hStmt);
+
+       hStmt = DBPrepare(g_hCoreDB, bNewObject ? _T("INSERT INTO slm_checks (check_id,type,content,threshold_id,state,reason) ")
+                                                                                         _T("VALUES (?,?,?,?,?,?)") :
+                                                                                         _T("UPDATE slm_checks SET check_id=?,type=?,content=?,threshold_id=?,state=?,reason=? ")
+                                                                                         _T("WHERE service_id=?"));
+       if (hStmt == NULL)      
+               goto finish;
+       DBBind(hStmt, 1, DB_SQLTYPE_INTEGER, m_dwId);
+       DBBind(hStmt, 2, DB_SQLTYPE_INTEGER, DWORD(m_type));
+       DBBind(hStmt, 3, DB_SQLTYPE_TEXT, m_script, DB_BIND_STATIC);
+       DBBind(hStmt, 4, DB_SQLTYPE_INTEGER, m_threshold ? m_threshold->getId() : 0);
+       DBBind(hStmt, 5, DB_SQLTYPE_INTEGER, DWORD(m_state));
+       DBBind(hStmt, 6, DB_SQLTYPE_VARCHAR, m_reason, DB_BIND_STATIC);
+       if (!bNewObject)
+               DBBind(hStmt, 7, DB_SQLTYPE_INTEGER, m_dwId);
+       
+       if (!DBExecute(hStmt))
+       {
+               DBFreeStatement(hStmt);
+               goto finish;
+       }
+
+       DBFreeResult(hResult);
+       DBFreeStatement(hStmt);
+
+       saveACLToDB(hdb);
+       ret = TRUE;
+
+finish:
+       // Unlock object and clear modification flag
+       m_bIsModified = FALSE;
+       UnlockData();
+       return ret;
+}
+
+
+//
+// Delete object from database
+//
+
+BOOL SlmCheck::DeleteFromDB()
+{
+       TCHAR szQuery[QUERY_LENGTH];
+       BOOL bSuccess;
+
+       bSuccess = NetObj::DeleteFromDB();
+       if (bSuccess)
+       {
+               _sntprintf(szQuery, QUERY_LENGTH, _T("DELETE FROM slm_checks WHERE check_id=%d"), m_dwId);
+               QueueSQLRequest(szQuery);
+       }
+
+       return bSuccess;
+}
+
+
+//
+// Create CSCP message with object's data
+//
+
+void SlmCheck::CreateMessage(CSCPMessage *pMsg)
+{
+       NetObj::CreateMessage(pMsg);
+       // pMsg->SetVariable(VID_ID, m_dwId);
+       // pMsg->SetVariable(VID_STATUS, m_svcStatus);
+}
+
+
+//
+// Modify object from message
+//
+
+DWORD SlmCheck::ModifyFromMessage(CSCPMessage *pRequest, BOOL bAlreadyLocked)
+{
+       if (!bAlreadyLocked)
+               LockData();
+
+       // if (pRequest->IsVariableExist(VID_STATUS))
+       //      m_svcStatus = pRequest->GetVariableLong(VID_STATUS);
+
+       return NetObj::ModifyFromMessage(pRequest, TRUE);
+}
+
+
+//
+// Execute check
+//
+
+void SlmCheck::execute()
+{
+       NXSL_ServerEnv pEnv;
+       NXSL_Value *pValue;
+
+       switch (m_type)
+       {
+       case check_script:
+               if (m_pCompiledScript->run(&pEnv, 0, NULL) == 0)
+               {
+                       pValue = m_pCompiledScript->getResult();
+                       m_iStatus = pValue->getValueAsInt32() == 0 ? STATUS_NORMAL : STATUS_CRITICAL;
+                       DbgPrintf(9, _T("%s/%ld ret value %d"), m_szName, (long)m_dwId, pValue->getValueAsInt32());
+               }
+               else
+               {
+                       DbgPrintf(4, _T("%s/%ld nxsl run() failed, %s"),  m_szName, (long)m_dwId, m_pCompiledScript->getErrorText());
+               }
+               break;
+       case check_threshold:
+       default:
+               DbgPrintf(4, _T("execute() called for undefined check type, check %s/%ld"), m_szName, (long)m_dwId);
+               m_iStatus = STATUS_UNKNOWN;
+               break;
+       }
+}
+
index 0e7383a..8b889b4 100644 (file)
@@ -1588,6 +1588,7 @@ protected:
        TCHAR* m_script;
        BOOL m_state;
        TCHAR m_reason[256];
+       NXSL_Program *m_pCompiledScript;
 
 public:
        SlmCheck();
@@ -1604,6 +1605,7 @@ public:
        virtual void CreateMessage(CSCPMessage *pMsg);
        virtual DWORD ModifyFromMessage(CSCPMessage *pRequest, BOOL bAlreadyLocked = FALSE);
 
+       void execute();
        void setReason(const TCHAR* reason) { nx_strncpy(m_reason, reason, 255); }
        const TCHAR* getReason() const { return m_reason; }
 };
@@ -1631,6 +1633,7 @@ public:
 class NXCORE_EXPORTABLE BizService : public Container
 {
 protected:
+       bool m_busy;
 
 public:
        BizService();
@@ -1647,13 +1650,12 @@ public:
        virtual void CreateMessage(CSCPMessage *pMsg);
        virtual DWORD ModifyFromMessage(CSCPMessage *pRequest, BOOL bAlreadyLocked = FALSE);
 
-       bool isReadyForPolling();
-       void lockForPolling();
+       bool isReadyForPolling() { return !m_busy; }
+       void lockForPolling() { m_busy = true; }
        void poll(ClientSession *pSession, DWORD dwRqId, int nPoller);
 };
 
 
-
 //
 // Container category information
 //
index a3386bf..e59524c 100644 (file)
 #define AF_ENABLE_ZONING                  0x00000080
 #define AF_SYNC_NODE_NAMES_WITH_DNS       0x00000100
 #define AF_CHECK_TRUSTED_NODES            0x00000200
+#define AF_ENABLE_SLM                                    0x00040000
 #define AF_WRITE_FULL_DUMP                0x00080000
 #define AF_RESOLVE_NODE_NAMES             0x00100000
 #define AF_CATCH_EXCEPTIONS               0x00200000