Fri Jan 20 06:33:45 2012

Asterisk developer's documentation


security_events.c

Go to the documentation of this file.
00001 /*
00002  * Asterisk -- An open source telephony toolkit.
00003  *
00004  * Copyright (C) 2009, Digium, Inc.
00005  *
00006  * Russell Bryant <russell@digium.com>
00007  *
00008  * See http://www.asterisk.org for more information about
00009  * the Asterisk project. Please do not directly contact
00010  * any of the maintainers of this project for assistance;
00011  * the project provides a web site, mailing lists and IRC
00012  * channels for your use.
00013  *
00014  * This program is free software, distributed under the terms of
00015  * the GNU General Public License Version 2. See the LICENSE file
00016  * at the top of the source tree.
00017  */
00018 
00019 /*!
00020  * \file
00021  *
00022  * \brief Security Event Reporting Helpers
00023  *
00024  * \author Russell Bryant <russell@digium.com>
00025  */
00026 
00027 #include "asterisk.h"
00028 
00029 ASTERISK_FILE_VERSION(__FILE__, "$Revision: 337600 $")
00030 
00031 #include "asterisk/utils.h"
00032 #include "asterisk/strings.h"
00033 #include "asterisk/network.h"
00034 #include "asterisk/security_events.h"
00035 
00036 static const size_t TIMESTAMP_STR_LEN = 32;
00037 
00038 static const struct {
00039    const char *name;
00040    uint32_t version;
00041    enum ast_security_event_severity severity;
00042 #define MAX_SECURITY_IES 12
00043    struct ast_security_event_ie_type required_ies[MAX_SECURITY_IES];
00044    struct ast_security_event_ie_type optional_ies[MAX_SECURITY_IES];
00045 #undef MAX_SECURITY_IES
00046 } sec_events[AST_SECURITY_EVENT_NUM_TYPES] = {
00047 
00048 #define SEC_EVT_FIELD(e, field) (offsetof(struct ast_security_event_##e, field))
00049 
00050 [AST_SECURITY_EVENT_FAILED_ACL] = {
00051    .name     = "FailedACL",
00052    .version  = AST_SECURITY_EVENT_FAILED_ACL_VERSION,
00053    .severity = AST_SECURITY_EVENT_SEVERITY_ERROR,
00054    .required_ies = {
00055       { AST_EVENT_IE_EVENT_TV, 0 },
00056       { AST_EVENT_IE_SEVERITY, 0 },
00057       { AST_EVENT_IE_SERVICE, SEC_EVT_FIELD(common, service) },
00058       { AST_EVENT_IE_EVENT_VERSION, SEC_EVT_FIELD(common, version) },
00059       { AST_EVENT_IE_ACCOUNT_ID, SEC_EVT_FIELD(common, account_id) },
00060       { AST_EVENT_IE_SESSION_ID, SEC_EVT_FIELD(common, session_id) },
00061       { AST_EVENT_IE_LOCAL_ADDR, SEC_EVT_FIELD(common, local_addr) },
00062       { AST_EVENT_IE_REMOTE_ADDR, SEC_EVT_FIELD(common, remote_addr) },
00063       { AST_EVENT_IE_END, 0 }
00064    },
00065    .optional_ies = {
00066       { AST_EVENT_IE_MODULE, SEC_EVT_FIELD(common, module) },
00067       { AST_EVENT_IE_ACL_NAME, SEC_EVT_FIELD(failed_acl, acl_name) },
00068       { AST_EVENT_IE_SESSION_TV, SEC_EVT_FIELD(common, session_tv) },
00069       { AST_EVENT_IE_END, 0 }
00070    },
00071 },
00072 
00073 [AST_SECURITY_EVENT_INVAL_ACCT_ID] = {
00074    .name     = "InvalidAccountID",
00075    .version  = AST_SECURITY_EVENT_INVAL_ACCT_ID_VERSION,
00076    .severity = AST_SECURITY_EVENT_SEVERITY_ERROR,
00077    .required_ies = {
00078       { AST_EVENT_IE_EVENT_TV, 0 },
00079       { AST_EVENT_IE_SEVERITY, 0 },
00080       { AST_EVENT_IE_SERVICE, SEC_EVT_FIELD(common, service) },
00081       { AST_EVENT_IE_EVENT_VERSION, SEC_EVT_FIELD(common, version) },
00082       { AST_EVENT_IE_ACCOUNT_ID, SEC_EVT_FIELD(common, account_id) },
00083       { AST_EVENT_IE_SESSION_ID, SEC_EVT_FIELD(common, session_id) },
00084       { AST_EVENT_IE_LOCAL_ADDR, SEC_EVT_FIELD(common, local_addr) },
00085       { AST_EVENT_IE_REMOTE_ADDR, SEC_EVT_FIELD(common, remote_addr) },
00086       { AST_EVENT_IE_END, 0 }
00087    },
00088    .optional_ies = {
00089       { AST_EVENT_IE_MODULE, SEC_EVT_FIELD(common, module) },
00090       { AST_EVENT_IE_SESSION_TV, SEC_EVT_FIELD(common, session_tv) },
00091       { AST_EVENT_IE_END, 0 }
00092    },
00093 },
00094 
00095 [AST_SECURITY_EVENT_SESSION_LIMIT] = {
00096    .name     = "SessionLimit",
00097    .version  = AST_SECURITY_EVENT_SESSION_LIMIT_VERSION,
00098    .severity = AST_SECURITY_EVENT_SEVERITY_ERROR,
00099    .required_ies = {
00100       { AST_EVENT_IE_EVENT_TV, 0 },
00101       { AST_EVENT_IE_SEVERITY, 0 },
00102       { AST_EVENT_IE_SERVICE, SEC_EVT_FIELD(common, service) },
00103       { AST_EVENT_IE_EVENT_VERSION, SEC_EVT_FIELD(common, version) },
00104       { AST_EVENT_IE_ACCOUNT_ID, SEC_EVT_FIELD(common, account_id) },
00105       { AST_EVENT_IE_SESSION_ID, SEC_EVT_FIELD(common, session_id) },
00106       { AST_EVENT_IE_LOCAL_ADDR, SEC_EVT_FIELD(common, local_addr) },
00107       { AST_EVENT_IE_REMOTE_ADDR, SEC_EVT_FIELD(common, remote_addr) },
00108       { AST_EVENT_IE_END, 0 }
00109    },
00110    .optional_ies = {
00111       { AST_EVENT_IE_MODULE, SEC_EVT_FIELD(common, module) },
00112       { AST_EVENT_IE_SESSION_TV, SEC_EVT_FIELD(common, session_tv) },
00113       { AST_EVENT_IE_END, 0 }
00114    },
00115 },
00116 
00117 [AST_SECURITY_EVENT_MEM_LIMIT] = {
00118    .name     = "MemoryLimit",
00119    .version  = AST_SECURITY_EVENT_MEM_LIMIT_VERSION,
00120    .severity = AST_SECURITY_EVENT_SEVERITY_ERROR,
00121    .required_ies = {
00122       { AST_EVENT_IE_EVENT_TV, 0 },
00123       { AST_EVENT_IE_SEVERITY, 0 },
00124       { AST_EVENT_IE_SERVICE, SEC_EVT_FIELD(common, service) },
00125       { AST_EVENT_IE_EVENT_VERSION, SEC_EVT_FIELD(common, version) },
00126       { AST_EVENT_IE_ACCOUNT_ID, SEC_EVT_FIELD(common, account_id) },
00127       { AST_EVENT_IE_SESSION_ID, SEC_EVT_FIELD(common, session_id) },
00128       { AST_EVENT_IE_LOCAL_ADDR, SEC_EVT_FIELD(common, local_addr) },
00129       { AST_EVENT_IE_REMOTE_ADDR, SEC_EVT_FIELD(common, remote_addr) },
00130       { AST_EVENT_IE_END, 0 }
00131    },
00132    .optional_ies = {
00133       { AST_EVENT_IE_MODULE, SEC_EVT_FIELD(common, module) },
00134       { AST_EVENT_IE_SESSION_TV, SEC_EVT_FIELD(common, session_tv) },
00135       { AST_EVENT_IE_END, 0 }
00136    },
00137 },
00138 
00139 [AST_SECURITY_EVENT_LOAD_AVG] = {
00140    .name     = "LoadAverageLimit",
00141    .version  = AST_SECURITY_EVENT_LOAD_AVG_VERSION,
00142    .severity = AST_SECURITY_EVENT_SEVERITY_ERROR,
00143    .required_ies = {
00144       { AST_EVENT_IE_EVENT_TV, 0 },
00145       { AST_EVENT_IE_SEVERITY, 0 },
00146       { AST_EVENT_IE_SERVICE, SEC_EVT_FIELD(common, service) },
00147       { AST_EVENT_IE_EVENT_VERSION, SEC_EVT_FIELD(common, version) },
00148       { AST_EVENT_IE_ACCOUNT_ID, SEC_EVT_FIELD(common, account_id) },
00149       { AST_EVENT_IE_SESSION_ID, SEC_EVT_FIELD(common, session_id) },
00150       { AST_EVENT_IE_LOCAL_ADDR, SEC_EVT_FIELD(common, local_addr) },
00151       { AST_EVENT_IE_REMOTE_ADDR, SEC_EVT_FIELD(common, remote_addr) },
00152       { AST_EVENT_IE_END, 0 }
00153    },
00154    .optional_ies = {
00155       { AST_EVENT_IE_MODULE, SEC_EVT_FIELD(common, module) },
00156       { AST_EVENT_IE_SESSION_TV, SEC_EVT_FIELD(common, session_tv) },
00157       { AST_EVENT_IE_END, 0 }
00158    },
00159 },
00160 
00161 [AST_SECURITY_EVENT_REQ_NO_SUPPORT] = {
00162    .name     = "RequestNotSupported",
00163    .version  = AST_SECURITY_EVENT_REQ_NO_SUPPORT_VERSION,
00164    .severity = AST_SECURITY_EVENT_SEVERITY_ERROR,
00165    .required_ies = {
00166       { AST_EVENT_IE_EVENT_TV, 0 },
00167       { AST_EVENT_IE_SEVERITY, 0 },
00168       { AST_EVENT_IE_SERVICE, SEC_EVT_FIELD(common, service) },
00169       { AST_EVENT_IE_EVENT_VERSION, SEC_EVT_FIELD(common, version) },
00170       { AST_EVENT_IE_ACCOUNT_ID, SEC_EVT_FIELD(common, account_id) },
00171       { AST_EVENT_IE_SESSION_ID, SEC_EVT_FIELD(common, session_id) },
00172       { AST_EVENT_IE_LOCAL_ADDR, SEC_EVT_FIELD(common, local_addr) },
00173       { AST_EVENT_IE_REMOTE_ADDR, SEC_EVT_FIELD(common, remote_addr) },
00174       { AST_EVENT_IE_REQUEST_TYPE, SEC_EVT_FIELD(req_no_support, request_type) },
00175       { AST_EVENT_IE_END, 0 }
00176    },
00177    .optional_ies = {
00178       { AST_EVENT_IE_MODULE, SEC_EVT_FIELD(common, module) },
00179       { AST_EVENT_IE_SESSION_TV, SEC_EVT_FIELD(common, session_tv) },
00180       { AST_EVENT_IE_END, 0 }
00181    },
00182 },
00183 
00184 [AST_SECURITY_EVENT_REQ_NOT_ALLOWED] = {
00185    .name     = "RequestNotAllowed",
00186    .version  = AST_SECURITY_EVENT_REQ_NOT_ALLOWED_VERSION,
00187    .severity = AST_SECURITY_EVENT_SEVERITY_ERROR,
00188    .required_ies = {
00189       { AST_EVENT_IE_EVENT_TV, 0 },
00190       { AST_EVENT_IE_SEVERITY, 0 },
00191       { AST_EVENT_IE_SERVICE, SEC_EVT_FIELD(common, service) },
00192       { AST_EVENT_IE_EVENT_VERSION, SEC_EVT_FIELD(common, version) },
00193       { AST_EVENT_IE_ACCOUNT_ID, SEC_EVT_FIELD(common, account_id) },
00194       { AST_EVENT_IE_SESSION_ID, SEC_EVT_FIELD(common, session_id) },
00195       { AST_EVENT_IE_LOCAL_ADDR, SEC_EVT_FIELD(common, local_addr) },
00196       { AST_EVENT_IE_REMOTE_ADDR, SEC_EVT_FIELD(common, remote_addr) },
00197       { AST_EVENT_IE_REQUEST_TYPE, SEC_EVT_FIELD(req_not_allowed, request_type) },
00198       { AST_EVENT_IE_END, 0 }
00199    },
00200    .optional_ies = {
00201       { AST_EVENT_IE_MODULE, SEC_EVT_FIELD(common, module) },
00202       { AST_EVENT_IE_SESSION_TV, SEC_EVT_FIELD(common, session_tv) },
00203       { AST_EVENT_IE_REQUEST_PARAMS, SEC_EVT_FIELD(req_not_allowed, request_params) },
00204       { AST_EVENT_IE_END, 0 }
00205    },
00206 },
00207 
00208 [AST_SECURITY_EVENT_AUTH_METHOD_NOT_ALLOWED] = {
00209    .name     = "AuthMethodNotAllowed",
00210    .version  = AST_SECURITY_EVENT_AUTH_METHOD_NOT_ALLOWED_VERSION,
00211    .severity = AST_SECURITY_EVENT_SEVERITY_ERROR,
00212    .required_ies = {
00213       { AST_EVENT_IE_EVENT_TV, 0 },
00214       { AST_EVENT_IE_SEVERITY, 0 },
00215       { AST_EVENT_IE_SERVICE, SEC_EVT_FIELD(common, service) },
00216       { AST_EVENT_IE_EVENT_VERSION, SEC_EVT_FIELD(common, version) },
00217       { AST_EVENT_IE_ACCOUNT_ID, SEC_EVT_FIELD(common, account_id) },
00218       { AST_EVENT_IE_SESSION_ID, SEC_EVT_FIELD(common, session_id) },
00219       { AST_EVENT_IE_LOCAL_ADDR, SEC_EVT_FIELD(common, local_addr) },
00220       { AST_EVENT_IE_REMOTE_ADDR, SEC_EVT_FIELD(common, remote_addr) },
00221       { AST_EVENT_IE_AUTH_METHOD, SEC_EVT_FIELD(auth_method_not_allowed, auth_method) },
00222       { AST_EVENT_IE_END, 0 }
00223    },
00224    .optional_ies = {
00225       { AST_EVENT_IE_MODULE, SEC_EVT_FIELD(common, module) },
00226       { AST_EVENT_IE_SESSION_TV, SEC_EVT_FIELD(common, session_tv) },
00227       { AST_EVENT_IE_END, 0 }
00228    },
00229 },
00230 
00231 [AST_SECURITY_EVENT_REQ_BAD_FORMAT] = {
00232    .name     = "RequestBadFormat",
00233    .version  = AST_SECURITY_EVENT_REQ_BAD_FORMAT_VERSION,
00234    .severity = AST_SECURITY_EVENT_SEVERITY_ERROR,
00235    .required_ies = {
00236       { AST_EVENT_IE_EVENT_TV, 0 },
00237       { AST_EVENT_IE_SEVERITY, 0 },
00238       { AST_EVENT_IE_SERVICE, SEC_EVT_FIELD(common, service) },
00239       { AST_EVENT_IE_EVENT_VERSION, SEC_EVT_FIELD(common, version) },
00240       { AST_EVENT_IE_SESSION_ID, SEC_EVT_FIELD(common, session_id) },
00241       { AST_EVENT_IE_LOCAL_ADDR, SEC_EVT_FIELD(common, local_addr) },
00242       { AST_EVENT_IE_REMOTE_ADDR, SEC_EVT_FIELD(common, remote_addr) },
00243       { AST_EVENT_IE_REQUEST_TYPE, SEC_EVT_FIELD(req_bad_format, request_type) },
00244       { AST_EVENT_IE_END, 0 }
00245    },
00246    .optional_ies = {
00247       { AST_EVENT_IE_MODULE, SEC_EVT_FIELD(common, module) },
00248       { AST_EVENT_IE_SESSION_TV, SEC_EVT_FIELD(common, session_tv) },
00249       { AST_EVENT_IE_ACCOUNT_ID, SEC_EVT_FIELD(common, account_id) },
00250       { AST_EVENT_IE_REQUEST_PARAMS, SEC_EVT_FIELD(req_bad_format, request_params) },
00251       { AST_EVENT_IE_END, 0 }
00252    },
00253 },
00254 
00255 [AST_SECURITY_EVENT_SUCCESSFUL_AUTH] = {
00256    .name     = "SuccessfulAuth",
00257    .version  = AST_SECURITY_EVENT_SUCCESSFUL_AUTH_VERSION,
00258    .severity = AST_SECURITY_EVENT_SEVERITY_INFO,
00259    .required_ies = {
00260       { AST_EVENT_IE_EVENT_TV, 0 },
00261       { AST_EVENT_IE_SEVERITY, 0 },
00262       { AST_EVENT_IE_SERVICE, SEC_EVT_FIELD(common, service) },
00263       { AST_EVENT_IE_EVENT_VERSION, SEC_EVT_FIELD(common, version) },
00264       { AST_EVENT_IE_ACCOUNT_ID, SEC_EVT_FIELD(common, account_id) },
00265       { AST_EVENT_IE_SESSION_ID, SEC_EVT_FIELD(common, session_id) },
00266       { AST_EVENT_IE_LOCAL_ADDR, SEC_EVT_FIELD(common, local_addr) },
00267       { AST_EVENT_IE_REMOTE_ADDR, SEC_EVT_FIELD(common, remote_addr) },
00268       { AST_EVENT_IE_USING_PASSWORD, SEC_EVT_FIELD(successful_auth, using_password) },
00269       { AST_EVENT_IE_END, 0 }
00270    },
00271    .optional_ies = {
00272       { AST_EVENT_IE_MODULE, SEC_EVT_FIELD(common, module) },
00273       { AST_EVENT_IE_SESSION_TV, SEC_EVT_FIELD(common, session_tv) },
00274       { AST_EVENT_IE_END, 0 }
00275    },
00276 },
00277 
00278 [AST_SECURITY_EVENT_UNEXPECTED_ADDR] = {
00279    .name     = "UnexpectedAddress",
00280    .version  = AST_SECURITY_EVENT_UNEXPECTED_ADDR_VERSION,
00281    .severity = AST_SECURITY_EVENT_SEVERITY_ERROR,
00282    .required_ies = {
00283       { AST_EVENT_IE_EVENT_TV, 0 },
00284       { AST_EVENT_IE_SEVERITY, 0 },
00285       { AST_EVENT_IE_SERVICE, SEC_EVT_FIELD(common, service) },
00286       { AST_EVENT_IE_EVENT_VERSION, SEC_EVT_FIELD(common, version) },
00287       { AST_EVENT_IE_ACCOUNT_ID, SEC_EVT_FIELD(common, account_id) },
00288       { AST_EVENT_IE_SESSION_ID, SEC_EVT_FIELD(common, session_id) },
00289       { AST_EVENT_IE_LOCAL_ADDR, SEC_EVT_FIELD(common, local_addr) },
00290       { AST_EVENT_IE_REMOTE_ADDR, SEC_EVT_FIELD(common, remote_addr) },
00291       { AST_EVENT_IE_EXPECTED_ADDR, SEC_EVT_FIELD(unexpected_addr, expected_addr) },
00292       { AST_EVENT_IE_END, 0 }
00293    },
00294    .optional_ies = {
00295       { AST_EVENT_IE_MODULE, SEC_EVT_FIELD(common, module) },
00296       { AST_EVENT_IE_SESSION_TV, SEC_EVT_FIELD(common, session_tv) },
00297       { AST_EVENT_IE_END, 0 }
00298    },
00299 },
00300 
00301 [AST_SECURITY_EVENT_CHAL_RESP_FAILED] = {
00302    .name     = "ChallengeResponseFailed",
00303    .version  = AST_SECURITY_EVENT_CHAL_RESP_FAILED_VERSION,
00304    .severity = AST_SECURITY_EVENT_SEVERITY_ERROR,
00305    .required_ies = {
00306       { AST_EVENT_IE_EVENT_TV, 0 },
00307       { AST_EVENT_IE_SEVERITY, 0 },
00308       { AST_EVENT_IE_SERVICE, SEC_EVT_FIELD(common, service) },
00309       { AST_EVENT_IE_EVENT_VERSION, SEC_EVT_FIELD(common, version) },
00310       { AST_EVENT_IE_ACCOUNT_ID, SEC_EVT_FIELD(common, account_id) },
00311       { AST_EVENT_IE_SESSION_ID, SEC_EVT_FIELD(common, session_id) },
00312       { AST_EVENT_IE_LOCAL_ADDR, SEC_EVT_FIELD(common, local_addr) },
00313       { AST_EVENT_IE_REMOTE_ADDR, SEC_EVT_FIELD(common, remote_addr) },
00314       { AST_EVENT_IE_CHALLENGE, SEC_EVT_FIELD(chal_resp_failed, challenge) },
00315       { AST_EVENT_IE_RESPONSE, SEC_EVT_FIELD(chal_resp_failed, response) },
00316       { AST_EVENT_IE_EXPECTED_RESPONSE, SEC_EVT_FIELD(chal_resp_failed, expected_response) },
00317       { AST_EVENT_IE_END, 0 }
00318    },
00319    .optional_ies = {
00320       { AST_EVENT_IE_MODULE, SEC_EVT_FIELD(common, module) },
00321       { AST_EVENT_IE_SESSION_TV, SEC_EVT_FIELD(common, session_tv) },
00322       { AST_EVENT_IE_END, 0 }
00323    },
00324 },
00325 
00326 [AST_SECURITY_EVENT_INVAL_PASSWORD] = {
00327    .name     = "InvalidPassword",
00328    .version  = AST_SECURITY_EVENT_INVAL_PASSWORD_VERSION,
00329    .severity = AST_SECURITY_EVENT_SEVERITY_ERROR,
00330    .required_ies = {
00331       { AST_EVENT_IE_EVENT_TV, 0 },
00332       { AST_EVENT_IE_SEVERITY, 0 },
00333       { AST_EVENT_IE_SERVICE, SEC_EVT_FIELD(common, service) },
00334       { AST_EVENT_IE_EVENT_VERSION, SEC_EVT_FIELD(common, version) },
00335       { AST_EVENT_IE_ACCOUNT_ID, SEC_EVT_FIELD(common, account_id) },
00336       { AST_EVENT_IE_SESSION_ID, SEC_EVT_FIELD(common, session_id) },
00337       { AST_EVENT_IE_LOCAL_ADDR, SEC_EVT_FIELD(common, local_addr) },
00338       { AST_EVENT_IE_REMOTE_ADDR, SEC_EVT_FIELD(common, remote_addr) },
00339       { AST_EVENT_IE_CHALLENGE, SEC_EVT_FIELD(inval_password, challenge) },
00340       { AST_EVENT_IE_RECEIVED_CHALLENGE, SEC_EVT_FIELD(inval_password, received_challenge) },
00341       { AST_EVENT_IE_RECEIVED_HASH, SEC_EVT_FIELD(inval_password, received_hash) },
00342       { AST_EVENT_IE_END, 0 }
00343    },
00344    .optional_ies = {
00345       { AST_EVENT_IE_MODULE, SEC_EVT_FIELD(common, module) },
00346       { AST_EVENT_IE_SESSION_TV, SEC_EVT_FIELD(common, session_tv) },
00347       { AST_EVENT_IE_END, 0 }
00348    },
00349 },
00350 
00351 [AST_SECURITY_EVENT_CHAL_SENT] = {
00352    .name     = "ChallengeSent",
00353    .version  = AST_SECURITY_EVENT_CHAL_SENT_VERSION,
00354    .severity = AST_SECURITY_EVENT_SEVERITY_INFO,
00355    .required_ies = {
00356       { AST_EVENT_IE_EVENT_TV, 0 },
00357       { AST_EVENT_IE_SEVERITY, 0 },
00358       { AST_EVENT_IE_SERVICE, SEC_EVT_FIELD(common, service) },
00359       { AST_EVENT_IE_EVENT_VERSION, SEC_EVT_FIELD(common, version) },
00360       { AST_EVENT_IE_ACCOUNT_ID, SEC_EVT_FIELD(common, account_id) },
00361       { AST_EVENT_IE_SESSION_ID, SEC_EVT_FIELD(common, session_id) },
00362       { AST_EVENT_IE_LOCAL_ADDR, SEC_EVT_FIELD(common, local_addr) },
00363       { AST_EVENT_IE_REMOTE_ADDR, SEC_EVT_FIELD(common, remote_addr) },
00364       { AST_EVENT_IE_CHALLENGE, SEC_EVT_FIELD(chal_sent, challenge) },
00365       { AST_EVENT_IE_END, 0 }
00366    },
00367    .optional_ies = {
00368       { AST_EVENT_IE_MODULE, SEC_EVT_FIELD(common, module) },
00369       { AST_EVENT_IE_SESSION_TV, SEC_EVT_FIELD(common, session_tv) },
00370       { AST_EVENT_IE_END, 0 }
00371    },
00372 },
00373 
00374 [AST_SECURITY_EVENT_INVAL_TRANSPORT] = {
00375    .name     = "InvalidTransport",
00376    .version  = AST_SECURITY_EVENT_INVAL_TRANSPORT_VERSION,
00377    .severity = AST_SECURITY_EVENT_SEVERITY_ERROR,
00378    .required_ies = {
00379       { AST_EVENT_IE_EVENT_TV, 0 },
00380       { AST_EVENT_IE_SEVERITY, 0 },
00381       { AST_EVENT_IE_SERVICE, SEC_EVT_FIELD(common, service) },
00382       { AST_EVENT_IE_EVENT_VERSION, SEC_EVT_FIELD(common, version) },
00383       { AST_EVENT_IE_ACCOUNT_ID, SEC_EVT_FIELD(common, account_id) },
00384       { AST_EVENT_IE_SESSION_ID, SEC_EVT_FIELD(common, session_id) },
00385       { AST_EVENT_IE_LOCAL_ADDR, SEC_EVT_FIELD(common, local_addr) },
00386       { AST_EVENT_IE_REMOTE_ADDR, SEC_EVT_FIELD(common, remote_addr) },
00387       { AST_EVENT_IE_ATTEMPTED_TRANSPORT, SEC_EVT_FIELD(inval_transport, transport) },
00388       { AST_EVENT_IE_END, 0 }
00389    },
00390    .optional_ies = {
00391       { AST_EVENT_IE_MODULE, SEC_EVT_FIELD(common, module) },
00392       { AST_EVENT_IE_SESSION_TV, SEC_EVT_FIELD(common, session_tv) },
00393       { AST_EVENT_IE_END, 0 }
00394    },
00395 },
00396 
00397 #undef SEC_EVT_FIELD
00398 
00399 };
00400 
00401 static const struct {
00402    enum ast_security_event_severity severity;
00403    const char *str;
00404 } severities[] = {
00405    { AST_SECURITY_EVENT_SEVERITY_INFO,  "Informational" },
00406    { AST_SECURITY_EVENT_SEVERITY_ERROR, "Error" },
00407 };
00408 
00409 const char *ast_security_event_severity_get_name(
00410       const enum ast_security_event_severity severity)
00411 {
00412    unsigned int i;
00413 
00414    for (i = 0; i < ARRAY_LEN(severities); i++) {
00415       if (severities[i].severity == severity) {
00416          return severities[i].str;
00417       }
00418    }
00419 
00420    return NULL;
00421 }
00422 
00423 static int check_event_type(const enum ast_security_event_type event_type)
00424 {
00425    if (event_type < 0 || event_type >= AST_SECURITY_EVENT_NUM_TYPES) {
00426       ast_log(LOG_ERROR, "Invalid security event type %u\n", event_type);
00427       return -1;
00428    }
00429 
00430    return 0;
00431 }
00432 
00433 const char *ast_security_event_get_name(const enum ast_security_event_type event_type)
00434 {
00435    if (check_event_type(event_type)) {
00436       return NULL;
00437    }
00438 
00439    return sec_events[event_type].name;
00440 }
00441 
00442 const struct ast_security_event_ie_type *ast_security_event_get_required_ies(
00443       const enum ast_security_event_type event_type)
00444 {
00445    if (check_event_type(event_type)) {
00446       return NULL;
00447    }
00448 
00449    return sec_events[event_type].required_ies;
00450 }
00451 
00452 const struct ast_security_event_ie_type *ast_security_event_get_optional_ies(
00453       const enum ast_security_event_type event_type)
00454 {
00455    if (check_event_type(event_type)) {
00456       return NULL;
00457    }
00458 
00459    return sec_events[event_type].optional_ies;
00460 }
00461 
00462 static void encode_timestamp(struct ast_str **str, const struct timeval *tv)
00463 {
00464    ast_str_set(str, 0, "%u-%u",
00465          (unsigned int) tv->tv_sec,
00466          (unsigned int) tv->tv_usec);
00467 }
00468 
00469 static struct ast_event *alloc_event(const struct ast_security_event_common *sec)
00470 {
00471    struct ast_str *str = ast_str_alloca(TIMESTAMP_STR_LEN);
00472    struct timeval tv = ast_tvnow();
00473    const char *severity_str;
00474 
00475    if (check_event_type(sec->event_type)) {
00476       return NULL;
00477    }
00478 
00479    encode_timestamp(&str, &tv);
00480 
00481    severity_str = S_OR(
00482       ast_security_event_severity_get_name(sec_events[sec->event_type].severity),
00483       "Unknown"
00484    );
00485 
00486    return ast_event_new(AST_EVENT_SECURITY,
00487       AST_EVENT_IE_SECURITY_EVENT, AST_EVENT_IE_PLTYPE_UINT, sec->event_type,
00488       AST_EVENT_IE_EVENT_VERSION, AST_EVENT_IE_PLTYPE_UINT, sec->version,
00489       AST_EVENT_IE_EVENT_TV, AST_EVENT_IE_PLTYPE_STR, str->str,
00490       AST_EVENT_IE_SERVICE, AST_EVENT_IE_PLTYPE_STR, sec->service,
00491       AST_EVENT_IE_SEVERITY, AST_EVENT_IE_PLTYPE_STR, severity_str,
00492       AST_EVENT_IE_END);
00493 }
00494 
00495 static int add_timeval_ie(struct ast_event **event, enum ast_event_ie_type ie_type,
00496       const struct timeval *tv)
00497 {
00498    struct ast_str *str = ast_str_alloca(TIMESTAMP_STR_LEN);
00499 
00500    encode_timestamp(&str, tv);
00501 
00502    return ast_event_append_ie_str(event, ie_type, ast_str_buffer(str));
00503 }
00504 
00505 static int add_ipv4_ie(struct ast_event **event, enum ast_event_ie_type ie_type,
00506       const struct ast_security_event_ipv4_addr *addr)
00507 {
00508    struct ast_str *str = ast_str_alloca(64);
00509 
00510    ast_str_set(&str, 0, "IPV4/");
00511 
00512    switch (addr->transport) {
00513    case AST_SECURITY_EVENT_TRANSPORT_UDP:
00514       ast_str_append(&str, 0, "UDP/");
00515       break;
00516    case AST_SECURITY_EVENT_TRANSPORT_TCP:
00517       ast_str_append(&str, 0, "TCP/");
00518       break;
00519    case AST_SECURITY_EVENT_TRANSPORT_TLS:
00520       ast_str_append(&str, 0, "TLS/");
00521       break;
00522    }
00523 
00524    ast_str_append(&str, 0, "%s/%hu",
00525          ast_inet_ntoa(addr->sin->sin_addr),
00526          ntohs(addr->sin->sin_port));
00527 
00528    return ast_event_append_ie_str(event, ie_type, ast_str_buffer(str));
00529 }
00530 
00531 enum ie_required {
00532    NOT_REQUIRED,
00533    REQUIRED
00534 };
00535 
00536 static int add_ie(struct ast_event **event, const struct ast_security_event_common *sec,
00537       const struct ast_security_event_ie_type *ie_type, enum ie_required req)
00538 {
00539    int res = 0;
00540 
00541    switch (ie_type->ie_type) {
00542    case AST_EVENT_IE_SERVICE:
00543    case AST_EVENT_IE_ACCOUNT_ID:
00544    case AST_EVENT_IE_SESSION_ID:
00545    case AST_EVENT_IE_MODULE:
00546    case AST_EVENT_IE_ACL_NAME:
00547    case AST_EVENT_IE_REQUEST_TYPE:
00548    case AST_EVENT_IE_REQUEST_PARAMS:
00549    case AST_EVENT_IE_AUTH_METHOD:
00550    case AST_EVENT_IE_CHALLENGE:
00551    case AST_EVENT_IE_RESPONSE:
00552    case AST_EVENT_IE_EXPECTED_RESPONSE:
00553    case AST_EVENT_IE_RECEIVED_CHALLENGE:
00554    case AST_EVENT_IE_RECEIVED_HASH:
00555    case AST_EVENT_IE_ATTEMPTED_TRANSPORT:
00556    {
00557       const char *str;
00558 
00559       str = *((const char **)(((const char *) sec) + ie_type->offset));
00560 
00561       if (req && !str) {
00562          ast_log(LOG_WARNING, "Required IE '%d' for security event "
00563                "type '%d' not present\n", ie_type->ie_type,
00564                sec->event_type);
00565          res = -1;
00566       }
00567 
00568       if (str) {
00569          res = ast_event_append_ie_str(event, ie_type->ie_type, str);
00570       }
00571 
00572       break;
00573    }
00574    case AST_EVENT_IE_EVENT_VERSION:
00575    case AST_EVENT_IE_USING_PASSWORD:
00576    {
00577       uint32_t val;
00578       val = *((const uint32_t *)(((const char *) sec) + ie_type->offset));
00579       res = ast_event_append_ie_uint(event, ie_type->ie_type, val);
00580       break;
00581    }
00582    case AST_EVENT_IE_LOCAL_ADDR:
00583    case AST_EVENT_IE_REMOTE_ADDR:
00584    case AST_EVENT_IE_EXPECTED_ADDR:
00585    {
00586       const struct ast_security_event_ipv4_addr *addr;
00587 
00588       addr = (const struct ast_security_event_ipv4_addr *)(((const char *) sec) + ie_type->offset);
00589 
00590       if (req && !addr->sin) {
00591          ast_log(LOG_WARNING, "Required IE '%d' for security event "
00592                "type '%d' not present\n", ie_type->ie_type,
00593                sec->event_type);
00594          res = -1;
00595       }
00596 
00597       if (addr->sin) {
00598          res = add_ipv4_ie(event, ie_type->ie_type, addr);
00599       }
00600       break;
00601    }
00602    case AST_EVENT_IE_SESSION_TV:
00603    {
00604       const struct timeval *tval;
00605 
00606       tval = *((const struct timeval **)(((const char *) sec) + ie_type->offset));
00607 
00608       if (req && !tval) {
00609          ast_log(LOG_WARNING, "Required IE '%d' for security event "
00610                "type '%d' not present\n", ie_type->ie_type,
00611                sec->event_type);
00612          res = -1;
00613       }
00614 
00615       if (tval) {
00616          add_timeval_ie(event, ie_type->ie_type, tval);
00617       }
00618 
00619       break;
00620    }
00621    case AST_EVENT_IE_EVENT_TV:
00622    case AST_EVENT_IE_SEVERITY:
00623       /* Added automatically, nothing to do here. */
00624       break;
00625    default:
00626       ast_log(LOG_WARNING, "Unhandled IE type '%d', this security event "
00627             "will be missing data.\n", ie_type->ie_type);
00628       break;
00629    }
00630 
00631    return res;
00632 }
00633 
00634 static int handle_security_event(const struct ast_security_event_common *sec)
00635 {
00636    struct ast_event *event;
00637    const struct ast_security_event_ie_type *ies;
00638    unsigned int i;
00639 
00640    if (!(event = alloc_event(sec))) {
00641       return -1;
00642    }
00643 
00644    for (ies = ast_security_event_get_required_ies(sec->event_type), i = 0;
00645          ies[i].ie_type != AST_EVENT_IE_END;
00646          i++) {
00647       if (add_ie(&event, sec, ies + i, REQUIRED)) {
00648          goto return_error;
00649       }
00650    }
00651 
00652    for (ies = ast_security_event_get_optional_ies(sec->event_type), i = 0;
00653          ies[i].ie_type != AST_EVENT_IE_END;
00654          i++) {
00655       if (add_ie(&event, sec, ies + i, NOT_REQUIRED)) {
00656          goto return_error;
00657       }
00658    }
00659 
00660 
00661    if (ast_event_queue(event)) {
00662       goto return_error;
00663    }
00664 
00665    return 0;
00666 
00667 return_error:
00668    if (event) {
00669       ast_event_destroy(event);
00670    }
00671 
00672    return -1;
00673 }
00674 
00675 int ast_security_event_report(const struct ast_security_event_common *sec)
00676 {
00677    int res;
00678 
00679    if (sec->event_type < 0 || sec->event_type >= AST_SECURITY_EVENT_NUM_TYPES) {
00680       ast_log(LOG_ERROR, "Invalid security event type\n");
00681       return -1;
00682    }
00683 
00684    if (!sec_events[sec->event_type].name) {
00685       ast_log(LOG_WARNING, "Security event type %u not handled\n",
00686             sec->event_type);
00687       return -1;
00688    }
00689 
00690    if (sec->version != sec_events[sec->event_type].version) {
00691       ast_log(LOG_WARNING, "Security event %u version mismatch\n",
00692             sec->event_type);
00693       return -1;
00694    }
00695 
00696    res = handle_security_event(sec);
00697 
00698    return res;
00699 }
00700 
00701 

Generated on Fri Jan 20 06:33:45 2012 for Asterisk - The Open Source Telephony Project by  doxygen 1.5.6