hbac_evaluator.c revision e0c86d21388bffe2e3919e780780c40d96186abb
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync IPA Backend Module -- Access control
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync Sumit Bose <sbose@redhat.com>
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync Stephen Gallagher <sgallagh@redhat.com>
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync Copyright (C) 2011 Red Hat
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync This program is free software; you can redistribute it and/or modify
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync it under the terms of the GNU General Public License as published by
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync the Free Software Foundation; either version 3 of the License, or
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync (at your option) any later version.
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync This program is distributed in the hope that it will be useful,
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync but WITHOUT ANY WARRANTY; without even the implied warranty of
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync GNU General Public License for more details.
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync You should have received a copy of the GNU General Public License
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync along with this program. If not, see <http://www.gnu.org/licenses/>.
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync#include "config.h" /* for HAVE_FUNCTION_ATTRIBUTE_FORMAT in "ipa_hbac.h" */
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync/* HBAC logging system */
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync/* debug macro */
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync/* static pointer to external logging function */
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync/* setup function for external logging function */
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsyncvoid hbac_enable_debug(hbac_debug_fn_t external_debug_fn)
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync/* auxiliary function for hbac_request_element logging */
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsyncstatic void hbac_request_element_debug_print(struct hbac_request_element *el,
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync const char *label);
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync/* auxiliary function for hbac_eval_req logging */
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsyncstatic void hbac_req_debug_print(struct hbac_eval_req *req);
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync/* auxiliary function for hbac_rule_element logging */
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsyncstatic void hbac_rule_element_debug_print(struct hbac_rule_element *el,
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync const char *label);
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync/* auxiliary function for hbac_rule logging */
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsyncstatic void hbac_rule_debug_print(struct hbac_rule *rule);
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync/* Placeholder structure for future HBAC time-based
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync * evaluation rules
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsyncstatic bool hbac_rule_element_is_complete(struct hbac_rule_element *el)
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync if (el->category == HBAC_CATEGORY_ALL) return true;
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync if (el->names == NULL && el->groups == NULL) return false;
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync return true;
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync /* If other categories are added, handle them here */
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync return false;
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsyncbool hbac_rule_is_complete(struct hbac_rule *rule, uint32_t *missing_attrs)
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync bool complete = true;
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync /* No rule passed in? */
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync return false;
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync /* Make sure we have all elements */
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync if (!hbac_rule_element_is_complete(rule->services)) {
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync if (!hbac_rule_element_is_complete(rule->targethosts)) {
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync if (!hbac_rule_element_is_complete(rule->srchosts)) {
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsyncenum hbac_eval_result_int hbac_evaluate_rule(struct hbac_rule *rule,
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsyncenum hbac_eval_result hbac_evaluate(struct hbac_rule **rules,
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync for (i = 0; rules[i]; i++) {
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync intermediate_result = hbac_evaluate_rule(rules[i], hbac_req, &ret);
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync /* This rule did not match at all. Skip it */
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync HBAC_DEBUG(HBAC_DBG_INFO, "The rule [%s] did not match.\n",
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync } else if (intermediate_result == HBAC_EVAL_MATCHED) {
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync HBAC_DEBUG(HBAC_DBG_INFO, "ALLOWED by rule [%s].\n", rules[i]->name);
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync /* An error occurred processing this rule */
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync "Error %d occurred during evaluating of rule [%s].\n",
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync /* Explicitly not checking the result of strdup(), since if
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync * it's NULL, we can't do anything anyway.
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync /* If we've reached the end of the loop, we have either set the
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync * result to ALLOW explicitly or we'll stick with the default DENY.
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsyncstatic errno_t hbac_evaluate_element(struct hbac_rule_element *rule_el,
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsyncenum hbac_eval_result_int hbac_evaluate_rule(struct hbac_rule *rule,
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync HBAC_DEBUG(HBAC_DBG_INFO, "Rule [%s] is not enabled\n", rule->name);
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync /* Make sure we have all elements */
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync "Rule [%s] cannot be parsed, some elements are empty\n",
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync /* Check users */
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync "Cannot parse user elements of rule [%s]\n", rule->name);
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync } else if (!matched) {
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync /* Check services */
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync "Cannot parse service elements of rule [%s]\n", rule->name);
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync } else if (!matched) {
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync /* Check target hosts */
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync "Cannot parse targethost elements of rule [%s]\n",
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync } else if (!matched) {
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync /* Check source hosts */
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync "Cannot parse srchost elements of rule [%s]\n",
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsync } else if (!matched) {
4fd606d1f5abe38e1f42c38de1d2e895166bd0f4vboxsyncstatic errno_t hbac_evaluate_element(struct hbac_rule_element *rule_el,
*matched = true;
return EOK;
return ret;
*matched = true;
return EOK;
return ret;
*matched = true;
return EOK;
*matched = false;
return EOK;
switch (result) {
case HBAC_EVAL_ALLOW:
case HBAC_EVAL_DENY:
case HBAC_EVAL_ERROR:
case HBAC_EVAL_OOM:
switch (code) {
case HBAC_SUCCESS:
case HBAC_ERROR_OUT_OF_MEMORY:
case HBAC_ERROR_UNKNOWN:
const char *label)
if (el) {
if (req) {
if (ret <= 0) {
const char *label)
if (el) {
if (rule) {