new upstream release (3.3.0); modify package compatibility for Stretch
[ossec-hids.git] / src / win32 / ui / common.c
index 7b16451..87049a4 100644 (file)
-/* @(#) $Id: common.c,v 1.13 2009/06/24 18:53:10 dcid Exp $ */
-
 /* Copyright (C) 2009 Trend Micro Inc.
  * All rights reserved.
  *
  * This program is a free software; you can redistribute it
  * and/or modify it under the terms of the GNU General Public
- * License (version 3) as published by the FSF - Free Software
+ * License (version 2) as published by the FSF - Free Software
  * Foundation.
- *
- * License details at the LICENSE file included with OSSEC or 
- * online at: http://www.ossec.net/en/licensing.html
  */
 
-
+#include "shared.h"
 #include "os_win32ui.h"
-#include "os_win.h"
+#include "../os_win.h"
 #include "os_xml/os_xml.h"
-#include "os_xml/os_xml_writer.h"
 #include "os_net/os_net.h"
 #include "validate_op.h"
-#include "shared.h"
 
 
-/* Generate server info (for the main status */
+/* Generate server info (for the main status) */
 int gen_server_info(HWND hwnd)
 {
-    memset(ui_server_info, '\0', 2048 +1);
-    snprintf(ui_server_info, 2048, 
-            "Agent: %s (%s)  -  %s\r\n\r\n"
-            "Status: %s",
-            config_inst.agentname, 
-            config_inst.agentid, 
-            config_inst.agentip,
-            config_inst.status);
-
-
-    /* Initializing top */
-    if(config_inst.version)
-    {
+    memset(ui_server_info, '\0', 2048 + 1);
+    snprintf(ui_server_info, 2048,
+             "Agent: %s (%s)  -  %s\r\n\r\n"
+             "Status: %s",
+             config_inst.agentname,
+             config_inst.agentid,
+             config_inst.agentip,
+             config_inst.status);
+
+    /* Initialize top */
+    if (config_inst.version) {
         SetDlgItemText(hwnd, UI_SERVER_TOP, config_inst.version);
         SetDlgItemText(hwnd, UI_SERVER_INFO, ui_server_info);
     }
-    
-    /* Initializing auth key */
+
+    /* Initialize auth key */
     SetDlgItemText(hwnd, UI_SERVER_AUTH, config_inst.key);
 
-    /* Initializing server ip */
+    /* Initialize server IP */
     SetDlgItemText(hwnd, UI_SERVER_TEXT, config_inst.server);
 
-    SendMessage(hStatus, SB_SETTEXT, 0, (LPARAM)"http://www.ossec.net");                                                                                    
-    return(0);
-}
+    /* Set status data */
+    SendMessage(hStatus, SB_SETTEXT, 0, (LPARAM)"http://www.ossec.net");
+    if (config_inst.install_date) {
+        SendMessage(hStatus, SB_SETTEXT, 1, (LPARAM)config_inst.install_date);
+    }
 
+    return (0);
+}
 
-/* Reads the first line of a specific file  --must free after */
+/* Read the first line of a specific file  --must free after */
 char *cat_file(char *file, FILE *fp2)
 {
     FILE *fp;
 
-    if(!fp2)
-    {
+    if (!fp2) {
         fp = fopen(file, "r");
-    }
-    else
-    {
+    } else {
         fp = fp2;
     }
 
-    if(fp)
-    {
-        char buf[1024 +1];
+    if (fp) {
+        char buf[1024 + 1];
         char *ret = NULL;
 
         buf[1024] = '\0';
-        if(fgets(buf, 1024, fp) != NULL)
-        {
+        if (fgets(buf, 1024, fp) != NULL) {
             ret = strchr(buf, '\n');
-            if(ret)
-            {
+            if (ret) {
                 *ret = '\0';
             }
             ret = strchr(buf, '\r');
-            if(ret)
-            {
+            if (ret) {
                 *ret = '\0';
             }
 
             ret = strdup(buf);
         }
 
-        if(!fp2)
-        {
+        if (!fp2) {
             fclose(fp);
         }
-        return(ret);
+        return (ret);
     }
 
-    return(NULL);
+    return (NULL);
 }
 
 
@@ -105,74 +92,63 @@ int is_file(char *file)
 {
     FILE *fp;
     fp = fopen(file, "r");
-    if(fp)
-    {
+    if (fp) {
         fclose(fp);
-        return(1);
+        return (1);
     }
-    return(0);
+    return (0);
 }
 
-
 /* Clear configuration */
 void config_clear()
 {
-       debug2("read config 1");
-    if(config_inst.version)
-    {
+    if (config_inst.version) {
         free(config_inst.version);
     }
 
-       debug2("read config 2");
-    if(config_inst.key)
-    {
+    if (config_inst.key) {
         free(config_inst.key);
     }
 
-       debug2("read config 3");
-    if(config_inst.agentid)
-    {
+    if (config_inst.agentid) {
         free(config_inst.agentid);
     }
 
-       debug2("read config 4");
-    if(config_inst.server)
-    {
+    if (config_inst.server) {
         free(config_inst.server);
     }
-       debug2("read config 5");
 
+    if (config_inst.install_date) {
+        free(config_inst.install_date);
+    }
 
-    /* Initializing config instance */
+    /* Initialize config instance */
     config_inst.dir = NULL;
     config_inst.key = FL_NOKEY;
     config_inst.server = strdup(FL_NOSERVER);
     config_inst.config = NULL;
 
     config_inst.agentid = NULL;
-    config_inst.agentname= NULL;
+    config_inst.agentname = NULL;
     config_inst.agentip = NULL;
 
     config_inst.version = NULL;
     config_inst.install_date = NULL;
     config_inst.status = ST_UNKNOWN;
     config_inst.msg_sent = 0;
-
-       debug2("read config 6");
 }
 
-
-/* Initializes the config */
+/* Initialize the config */
 void init_config()
 {
-    /* Initializing config instance */
+    /* Initialize config instance */
     config_inst.dir = NULL;
     config_inst.key = FL_NOKEY;
     config_inst.server = NULL;
     config_inst.config = NULL;
 
     config_inst.agentid = NULL;
-    config_inst.agentname= NULL;
+    config_inst.agentname = NULL;
     config_inst.agentip = NULL;
 
     config_inst.version = NULL;
@@ -181,118 +157,56 @@ void init_config()
     config_inst.msg_sent = 0;
     config_inst.admin_access = 1;
 
-
-    /* Checking if ui is on the right path */
-    if(!is_file(CONFIG))
-    {
-        chdir(DEFDIR);
-        if(!is_file(CONFIG))
-        {
-            config_inst.admin_access = -1;
-        }
-    }
-
-
-    /* Testing for permission - this is a vista thing. 
-     * For some reason vista is not reporting the return codes
-     * properly.
-     */
-    {
-        FILE *fp;
-        fp = fopen(CONFIG, "a");
-        if(fp)
-        {
-            fclose(fp);
-        }
-        else
-        {
+    /* Check if ui is on the right path and has the proper permissions */
+    if (!is_file(CONFIG)) {
+        if (chdir(DEFDIR)) {
             config_inst.admin_access = 0;
         }
 
-
-        fp = fopen(".test-file.tst", "w");
-        if(fp)
-        {
-            if(fprintf(fp, ".test\n") == -1)
-            {
-                config_inst.admin_access = 0;
-            }
-            
-            fclose(fp);
-
-            /* trying to open it to read. */
-            fp = fopen(".test-file.tst", "r");
-            if(fp)
-            {
-                fclose(fp);
-            }
-            else
-            {
-                config_inst.admin_access = 0;
-            }
-            
-            if(unlink(".test-file.tst"))
-            {
-                config_inst.admin_access = 0;
-            }
-        }
-        else
-        {
+        if (!is_file(CONFIG)) {
             config_inst.admin_access = 0;
         }
     }
 }
 
-
-/* Reads ossec config */
-int config_read(HWND hwnd)
+/* Read ossec config */
+int config_read(__attribute__((unused)) HWND hwnd)
 {
     char *tmp_str;
+    char *delim = " - ";
 
-    
-    /* Clearing config */
+    /* Clear config */
     config_clear();
 
-
-    /* Getting OSSEC status */
-    if(CheckServiceRunning())
-    {
+    /* Get OSSEC status */
+    if (CheckServiceRunning()) {
         config_inst.status = ST_RUNNING;
-    }
-    else
-    {
+    } else {
         config_inst.status = ST_STOPPED;
     }
 
-
-    /* Getting version/install date */
-    config_inst.version = cat_file(VERSION_FILE, NULL); 
-    if(config_inst.version)
-    {
-        config_inst.install_date = strchr(config_inst.version, '-');
-        if(config_inst.install_date)
-        {
+    /* Get version/install date */
+    config_inst.version = cat_file(VERSION_FILE, NULL);
+    if (config_inst.version) {
+        config_inst.install_date = strstr(config_inst.version, delim);
+        if (config_inst.install_date) {
             *config_inst.install_date = '\0';
-            config_inst.install_date++;
+            config_inst.install_date += strlen(delim);
         }
     }
 
-
-    /* Getting number of messages sent */
-    tmp_str = cat_file(SENDER_FILE, NULL); 
-    if(tmp_str)
-    {
+    /* Get number of messages sent */
+    tmp_str = cat_file(SENDER_FILE, NULL);
+    if (tmp_str) {
         unsigned long int tmp_val = 0;
         char *to_free = tmp_str;
 
         tmp_val = atol(tmp_str);
-        if(tmp_val)
-        {
+        if (tmp_val) {
             config_inst.msg_sent = tmp_val * 9999;
 
             tmp_str = strchr(tmp_str, ':');
-            if(tmp_str)
-            {
+            if (tmp_str) {
                 tmp_str++;
                 tmp_val = atol(tmp_str);
                 config_inst.msg_sent += tmp_val;
@@ -302,50 +216,42 @@ int config_read(HWND hwnd)
         free(to_free);
     }
 
-
-    /* Getting agent id, name and ip */
+    /* Get agent ID, name and IP */
     tmp_str = cat_file(AUTH_FILE, NULL);
-    if(tmp_str)
-    {
-        /* Getting base 64 */
-        config_inst.key = encode_base64(strlen(tmp_str),tmp_str);
-        if(config_inst.key == NULL)
-        {
+    if (tmp_str) {
+        /* Get base 64 */
+        config_inst.key = encode_base64(strlen(tmp_str), tmp_str);
+        if (config_inst.key == NULL) {
             config_inst.key = FL_NOKEY;
         }
 
-        /* Getting id */
+        /* Get ID */
         config_inst.agentid = tmp_str;
 
         tmp_str = strchr(tmp_str, ' ');
-        if(tmp_str)
-        {
+        if (tmp_str) {
             *tmp_str = '\0';
             tmp_str++;
 
-            /* Getting name */
+            /* Get name */
             config_inst.agentname = tmp_str;
             tmp_str = strchr(tmp_str, ' ');
-            if(tmp_str)
-            {
+            if (tmp_str) {
                 *tmp_str = '\0';
                 tmp_str++;
 
-                /* Getting ip */
+                /* Get IP */
                 config_inst.agentip = tmp_str;
 
                 tmp_str = strchr(tmp_str, ' ');
-                if(tmp_str)
-                {
+                if (tmp_str) {
                     *tmp_str = '\0';
                 }
             }
         }
     }
 
-
-    if(config_inst.agentip == NULL)    
-    {
+    if (config_inst.agentip == NULL) {
         config_inst.agentid = strdup(ST_NOTSET);
         config_inst.agentname = strdup("Auth key not imported.");
         config_inst.agentip = ST_NOTSET;
@@ -353,153 +259,257 @@ int config_read(HWND hwnd)
         config_inst.status = ST_MISSING_IMPORT;
     }
 
-
-    /* Getting server ip */
-    if(!get_ossec_server())
-    {
-        if(config_inst.status == ST_MISSING_IMPORT)
-        {
+    /* Get server IP */
+    if (!get_ossec_server()) {
+        if (strcmp(config_inst.status, ST_MISSING_IMPORT) == 0) {
             config_inst.status = ST_MISSING_ALL;
-        }
-        else
-        {
+        } else {
             config_inst.status = ST_MISSING_SERVER;
         }
     }
 
-    return(0);
+    return (0);
 }
 
-
 /* Get OSSEC Server IP */
 int get_ossec_server()
 {
     OS_XML xml;
-
     char *str = NULL;
 
-
     /* Definitions */
-    char *(xml_serverip[])={"ossec_config","client","server-ip", NULL};
-    char *(xml_serverhost[])={"ossec_config","client","server-hostname", NULL};
-
+    const char *(xml_serverip[]) = {"ossec_config", "client", "server-ip", NULL};
+    const char *(xml_serverhost[]) = {"ossec_config", "client", "server-hostname", NULL};
 
-    /* Reading XML */
-    if(OS_ReadXML(CONFIG, &xml) < 0)
-    {
-        return(0);
+    /* Read XML */
+    if (OS_ReadXML(CONFIG, &xml) < 0) {
+        return (0);
     }
 
-
     /* We need to remove the entry for the server */
-    if(config_inst.server)
-    {
+    if (config_inst.server) {
         free(config_inst.server);
         config_inst.server = NULL;
     }
     config_inst.server_type = 0;
 
-
-    /* Getting ip */
+    /* Get IP */
     str = OS_GetOneContentforElement(&xml, xml_serverip);
-    if(str && (OS_IsValidIP(str, NULL) == 1))
-    {
+    if (str && (OS_IsValidIP(str, NULL) == 1)) {
         config_inst.server_type = SERVER_IP_USED;
         config_inst.server = str;
 
         OS_ClearXML(&xml);
-        return(1);
+        return (1);
     }
-    /* If we dont find the ip, try the server-hostname */
-    else
-    {
-        if(str)
-        {
+    /* If we don't find the IP, try the server hostname */
+    else {
+        if (str) {
             free(str);
             str = NULL;
         }
-        
+
         str = OS_GetOneContentforElement(&xml, xml_serverhost);
-        if(str)
-        {
+        if (str) {
             char *s_ip;
             s_ip = OS_GetHost(str, 0);
-            if(s_ip)
-            {
-                /* Clearing the host memory */
+            if (s_ip) {
+                /* Clear the host memory */
                 free(s_ip);
 
-                /* Assigning the hostname to the server info */
+                /* Assign the hostname to the server info */
                 config_inst.server_type = SERVER_HOST_USED;
                 config_inst.server = str;
                 OS_ClearXML(&xml);
-                return(1);
+                return (1);
             }
             free(str);
         }
     }
 
-
-    /* Setting up final server name when not available */
+    /* Set up final server name when not available */
     config_inst.server = strdup(FL_NOSERVER);
-    
 
     OS_ClearXML(&xml);
-    return(0);
+    return (0);
 }
 
+/* Run a cmd.exe command */
+int run_cmd(char *cmd, HWND hwnd)
+{
+    int result;
+    int cmdlen;
+    STARTUPINFO si;
+    PROCESS_INFORMATION pi;
+    DWORD exit_code;
+
+    /* Build command */
+    cmdlen = strlen(COMSPEC) + 5 + strlen(cmd);
+    char finalcmd[cmdlen];
+    snprintf(finalcmd, cmdlen, "%s /c %s", COMSPEC, cmd);
+
+    /* Log command being run */
+    log2file("%s: INFO: Running the following command (%s)", ARGV0, finalcmd);
+
+    ZeroMemory(&si, sizeof(si));
+    si.cb = sizeof(si);
+    ZeroMemory(&pi, sizeof(pi));
+
+    if (!CreateProcess(NULL, finalcmd, NULL, NULL, FALSE, CREATE_NO_WINDOW, NULL, NULL,
+                       &si, &pi)) {
+        MessageBox(hwnd, "Unable to run command.",
+                   "Error -- Failure Running Command", MB_OK);
+        return (0);
+    }
+
+    /* Wait until process exits */
+    WaitForSingleObject(pi.hProcess, INFINITE);
+
+    /* Get exit code from command */
+    result = GetExitCodeProcess(pi.hProcess, &exit_code);
+
+    /* Close process and thread */
+    CloseHandle(pi.hProcess);
+    CloseHandle(pi.hThread);
+
+    if (!result) {
+        MessageBox(hwnd, "Could not determine exit code from command.",
+                   "Error -- Failure Running Command", MB_OK);
+
+        return (0);
+    }
+
+    return (exit_code);
+}
 
 /* Set OSSEC Server IP */
 int set_ossec_server(char *ip, HWND hwnd)
 {
-    char **xml_pt = NULL;
-    char *(xml_serverip[])={"ossec_config","client","server-ip", NULL};
-    char *(xml_serverhost[])={"ossec_config","client","server-hostname", NULL};
-    
-
-    /* Verifying IP Address */
-    if(OS_IsValidIP(ip, NULL) != 1)
-    {
+    const char **xml_pt = NULL;
+    const char *(xml_serverip[]) = {"ossec_config", "client", "server-ip", NULL};
+    const char *(xml_serverhost[]) = {"ossec_config", "client", "server-hostname", NULL};
+
+    char config_tmp[] = CONFIG;
+    char *conf_file = basename_ex(config_tmp);
+
+    char tmp_path[strlen(TMP_DIR) + 1 + strlen(conf_file) + 6 + 1];
+
+    snprintf(tmp_path, sizeof(tmp_path), "%s/%sXXXXXX", TMP_DIR, conf_file);
+
+    /* Verify IP Address */
+    if (OS_IsValidIP(ip, NULL) != 1) {
         char *s_ip;
         s_ip = OS_GetHost(ip, 0);
 
-        if(!s_ip)
-        {
-            MessageBox(hwnd, "Invalid Server IP Address.\r\n"
-                             "It must be the valid Ipv4 address of the "
-                             "OSSEC server or its resolvable hostname.",
-                             "Invalid Server IP Address.",MB_OK);
-            return(0);
+        if (!s_ip) {
+            MessageBox(hwnd, "Invalid Server.\r\n"
+                       "It must be the valid address of the "
+                       "OSSEC server or the resolvable hostname.",
+                       "Error -- Failure Setting IP", MB_OK);
+            return (0);
         }
         config_inst.server_type = SERVER_HOST_USED;
         xml_pt = xml_serverhost;
-    }
-    else
-    {
+    } else {
         config_inst.server_type = SERVER_IP_USED;
         xml_pt = xml_serverip;
     }
 
+    /* Create temporary file */
+    if (mkstemp_ex(tmp_path) == -1) {
+        MessageBox(hwnd, "Could not create temporary file.",
+                   "Error -- Failure Setting IP", MB_OK);
+        return (0);
+    }
 
-
-    /* Reading the XML. Printing error and line number */
-    if(OS_WriteXML(CONFIG, NEWCONFIG, xml_pt, 
-                   NULL, NULL, ip, 0) != 0)
-    {
+    /* Read the XML. Print error and line number. */
+    if (OS_WriteXML(CONFIG, tmp_path, xml_pt, NULL, ip) != 0) {
         MessageBox(hwnd, "Unable to set OSSEC Server IP Address.\r\n"
                    "(Internal error on the XML Write).",
-                   "Unable to set Server IP Address.",MB_OK);
-        return(0);
+                   "Error -- Failure Setting IP", MB_OK);
+
+        if (unlink(tmp_path)) {
+            MessageBox(hwnd, "Could not delete temporary file.",
+                       "Error -- Failure Deleting Temporary File", MB_OK);
+        }
+
+        return (0);
+    }
+
+    /* Rename config files */
+    if (rename_ex(CONFIG, LASTCONFIG)) {
+        MessageBox(hwnd, "Unable to backup configuration.",
+                   "Error -- Failure Backing Up Configuration", MB_OK);
+
+        if (unlink(tmp_path)) {
+            MessageBox(hwnd, "Could not delete temporary file.",
+                       "Error -- Failure Deleting Temporary File", MB_OK);
+        }
+
+        return (0);
     }
 
-    /* Renaming config files */
-    unlink(LASTCONFIG);
-    rename(CONFIG, LASTCONFIG);
-    rename(NEWCONFIG, CONFIG);
+    if (rename_ex(tmp_path, CONFIG)) {
+        MessageBox(hwnd, "Unable rename temporary file.",
+                   "Error -- Failure Renaming Temporary File", MB_OK);
+
+        if (unlink(tmp_path)) {
+            MessageBox(hwnd, "Could not delete temporary file.",
+                       "Error -- Failure Deleting Temporary File", MB_OK);
+        }
 
+        return (0);
+    }
 
-    return(1);
+    return (1);
 }
 
+/* Set OSSEC Authentication Key */
+int set_ossec_key(char *key, HWND hwnd)
+{
+    FILE *fp;
+
+    char auth_file_tmp[] = AUTH_FILE;
+    char *keys_file = basename_ex(auth_file_tmp);
+
+    char tmp_path[strlen(TMP_DIR) + 1 + strlen(keys_file) + 6 + 1];
+
+    snprintf(tmp_path, sizeof(tmp_path), "%s/%sXXXXXX", TMP_DIR, keys_file);
 
-/* EOF */
+    /* Create temporary file */
+    if (mkstemp_ex(tmp_path) == -1) {
+        MessageBox(hwnd, "Could not create temporary file.",
+                   "Error -- Failure Setting IP", MB_OK);
+        return (0);
+    }
+
+    fp = fopen(tmp_path, "w");
+    if (fp) {
+        fprintf(fp, "%s", key);
+        fclose(fp);
+    } else {
+        MessageBox(hwnd, "Could not open temporary file for write.",
+                   "Error -- Failure Importing Key", MB_OK);
+
+        if (unlink(tmp_path)) {
+            MessageBox(hwnd, "Could not delete temporary file.",
+                       "Error -- Failure Deleting Temporary File", MB_OK);
+        }
+
+        return (0);
+    }
+
+    if (rename_ex(tmp_path, AUTH_FILE)) {
+        MessageBox(hwnd, "Unable to rename temporary file.",
+                   "Error -- Failure Renaming Temporary File", MB_OK);
+
+        if (unlink(tmp_path)) {
+            MessageBox(hwnd, "Could not delete temporary file.",
+                       "Error -- Failure Deleting Temporary File", MB_OK);
+        }
+
+        return (0);
+    }
+
+    return (1);
+}