Annotation of embedaddon/strongswan/src/libimcv/plugins/imv_os/imv_os_database.c, revision 1.1.1.1

1.1       misho       1: /*
                      2:  * Copyright (C) 2012-2017 Andreas Steffen
                      3:  * HSR Hochschule fuer Technik Rapperswil
                      4:  *
                      5:  * This program is free software; you can redistribute it and/or modify it
                      6:  * under the terms of the GNU General Public License as published by the
                      7:  * Free Software Foundation; either version 2 of the License, or (at your
                      8:  * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
                      9:  *
                     10:  * This program is distributed in the hope that it will be useful, but
                     11:  * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
                     12:  * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
                     13:  * for more details.
                     14:  */
                     15: 
                     16: #define _GNU_SOURCE /* for stdndup() */
                     17: #include <string.h>
                     18: 
                     19: #include "imv_os_database.h"
                     20: 
                     21: #include <utils/debug.h>
                     22: 
                     23: typedef struct private_imv_os_database_t private_imv_os_database_t;
                     24: 
                     25: /**
                     26:  * Private data of a imv_os_database_t object.
                     27:  *
                     28:  */
                     29: struct private_imv_os_database_t {
                     30: 
                     31:        /**
                     32:         * Public imv_os_database_t interface.
                     33:         */
                     34:        imv_os_database_t public;
                     35: 
                     36:        /**
                     37:         * database instance
                     38:         */
                     39:        database_t *db;
                     40: 
                     41: };
                     42: 
                     43: METHOD(imv_os_database_t, check_packages, status_t,
                     44:        private_imv_os_database_t *this, imv_os_state_t *os_state,
                     45:        enumerator_t *package_enumerator)
                     46: {
                     47:        imv_state_t *state;
                     48:        imv_session_t *session;
                     49:        imv_os_info_t *os_info;
                     50:        os_type_t os_type;
                     51:        char *product, *package, *release, *cur_release;
                     52:        chunk_t name, version;
                     53:        int pid, gid, security, blacklist;
                     54:        int count = 0, count_ok = 0, count_security = 0, count_blacklist = 0;
                     55:        enumerator_t *e;
                     56:        status_t status = SUCCESS;
                     57:        bool found, match;
                     58: 
                     59:        state = &os_state->interface;
                     60:        session = state->get_session(state);
                     61:        session->get_session_id(session, &pid, NULL);
                     62:        os_info = session->get_os_info(session);
                     63:        os_type = os_info->get_type(os_info);
                     64:        product = os_info->get_info(os_info);
                     65: 
                     66:        if (os_type == OS_TYPE_ANDROID)
                     67:        {
                     68:                /*no package dependency on Android version */
                     69:                product = enum_to_name(os_type_names, os_type);
                     70: 
                     71:                /* Get primary key of product */
                     72:                e = this->db->query(this->db,
                     73:                                        "SELECT id FROM products WHERE name = ?",
                     74:                                        DB_TEXT, product, DB_INT);
                     75:                if (!e)
                     76:                {
                     77:                        return FAILED;
                     78:                }
                     79:                if (!e->enumerate(e, &pid))
                     80:                {
                     81:                        e->destroy(e);
                     82:                        return NOT_FOUND;
                     83:                }
                     84:                e->destroy(e);
                     85:        }
                     86:        DBG1(DBG_IMV, "processing installed '%s' packages", product);
                     87: 
                     88:        while (package_enumerator->enumerate(package_enumerator, &name, &version))
                     89:        {
                     90:                /* Convert package name chunk to a string */
                     91:                package = strndup(name.ptr, name.len);
                     92:                count++;
                     93: 
                     94:                /* Get primary key of package */
                     95:                e = this->db->query(this->db,
                     96:                                        "SELECT id FROM packages WHERE name = ?",
                     97:                                        DB_TEXT, package, DB_INT);
                     98:                if (!e)
                     99:                {
                    100:                        free(package);
                    101:                        return FAILED;
                    102:                }
                    103:                if (!e->enumerate(e, &gid))
                    104:                {
                    105:                        /* package not present in database for any product - skip */
                    106:                        DBG2(DBG_IMV, "package '%s' (%.*s) not found",
                    107:                                                   package, version.len, version.ptr);
                    108:                        free(package);
                    109:                        e->destroy(e);
                    110:                        continue;
                    111:                }
                    112:                e->destroy(e);
                    113: 
                    114:                /* Convert package version chunk to a string */
                    115:                release = strndup(version.ptr, version.len);
                    116: 
                    117:                /* Enumerate over all acceptable versions */
                    118:                e = this->db->query(this->db,
                    119:                                "SELECT release, security, blacklist FROM versions "
                    120:                                "WHERE product = ? AND package = ?",
                    121:                                DB_INT, pid, DB_INT, gid, DB_TEXT, DB_INT, DB_INT);
                    122:                if (!e)
                    123:                {
                    124:                        free(package);
                    125:                        free(release);
                    126:                        return FAILED;
                    127:                }
                    128:                found = FALSE;
                    129:                match = FALSE;
                    130: 
                    131:                while (e->enumerate(e, &cur_release, &security, &blacklist))
                    132:                {
                    133:                        found = TRUE;
                    134:                        if (streq(release, cur_release) || streq("*", cur_release))
                    135:                        {
                    136:                                match = TRUE;
                    137:                                break;
                    138:                        }
                    139:                }
                    140:                e->destroy(e);
                    141: 
                    142:                if (found)
                    143:                {
                    144:                        if (match)
                    145:                        {
                    146:                                if (blacklist)
                    147:                                {
                    148:                                        DBG1(DBG_IMV, "package '%s' (%s) is blacklisted",
                    149:                                                                   package, release);
                    150:                                        count_blacklist++;
                    151:                                        os_state->add_bad_package(os_state, package,
                    152:                                                                                          OS_PACKAGE_STATE_BLACKLIST);
                    153:                                }
                    154:                                else if (security)
                    155:                                {
                    156:                                        DBG1(DBG_IMV, "package '%s' (%s) is vulnerable",
                    157:                                                                   package, release);
                    158:                                        os_state->add_bad_package(os_state, package,
                    159:                                                                                          OS_PACKAGE_STATE_SECURITY);
                    160:                                        count_security++;
                    161:                                }
                    162:                                else
                    163:                                {
                    164:                                        DBG2(DBG_IMV, "package '%s' (%s) is ok",
                    165:                                                                   package, release);
                    166:                                        count_ok++;
                    167:                                }
                    168:                        }
                    169:                        else
                    170:                        {
                    171:                                DBG1(DBG_IMV, "package '%s' (%s) no match", package, release);
                    172:                        }
                    173:                }
                    174:                else
                    175:                {
                    176:                        DBG2(DBG_IMV, "package '%s' (%s) unknown", package, release);
                    177:                }
                    178:                free(package);
                    179:                free(release);
                    180:        }
                    181:        os_state->set_count(os_state, count, count_security, count_blacklist,
                    182:                                                count_ok);
                    183: 
                    184:        return status;
                    185: }
                    186: 
                    187: METHOD(imv_os_database_t, destroy, void,
                    188:        private_imv_os_database_t *this)
                    189: {
                    190:        free(this);
                    191: }
                    192: 
                    193: /**
                    194:  * See header
                    195:  */
                    196: imv_os_database_t *imv_os_database_create(imv_database_t *imv_db)
                    197: {
                    198:        private_imv_os_database_t *this;
                    199: 
                    200:        if (!imv_db)
                    201:        {
                    202:                return NULL;
                    203:        }
                    204: 
                    205:        INIT(this,
                    206:                .public = {
                    207:                        .check_packages = _check_packages,
                    208:                        .destroy = _destroy,
                    209:                },
                    210:                .db = imv_db->get_database(imv_db),
                    211:        );
                    212: 
                    213:        return &this->public;
                    214: }
                    215: 

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>