/* SSSD Authors: Stephen Gallagher Copyright (C) 2011 Red Hat 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 3 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, see . */ #include #include #include #include #include #include #include "tests/common_check.h" #include "providers/ipa/ipa_hbac.h" #define HBAC_TEST_USER "testuser" #define HBAC_TEST_INVALID_USER "nosuchuser" #define HBAC_TEST_GROUP1 "testgroup1" #define HBAC_TEST_GROUP2 "testgroup2" #define HBAC_TEST_INVALID_GROUP "nosuchgroup" #define HBAC_TEST_SERVICE "testservice" #define HBAC_TEST_INVALID_SERVICE "nosuchservice" #define HBAC_TEST_SERVICEGROUP1 "login_services" #define HBAC_TEST_SERVICEGROUP2 "all_services" #define HBAC_TEST_INVALID_SERVICEGROUP "nosuchservicegroup" #define HBAC_TEST_SRCHOST "client.example.com" #define HBAC_TEST_INVALID_SRCHOST "nosuchsrchost" #define HBAC_TEST_SRCHOSTGROUP1 "site_hosts" #define HBAC_TEST_SRCHOSTGROUP2 "corp_hosts" #define HBAC_TEST_INVALID_SRCHOSTGROUP "nosuchsrchostgroup" /* These don't make sense for a user/group/service but they do the job and * every one is from a different codepage */ /* Latin Extended A - "Czech" */ const uint8_t user_utf8_lowcase[] = { 0xC4, 0x8D, 'e', 'c', 'h', 0x0 }; const uint8_t user_utf8_upcase[] = { 0xC4, 0x8C, 'e', 'c', 'h', 0x0 }; const uint8_t user_utf8_lowcase_neg[] = { 0xC4, 0x8E, 'e', 'c', 'h', 0x0 }; /* Latin 1 Supplement - "Munchen" */ const uint8_t service_utf8_lowcase[] = { 'm', 0xC3, 0xBC, 'n', 'c', 'h', 'e', 'n', 0x0 }; const uint8_t service_utf8_upcase[] = { 'M', 0xC3, 0x9C, 'N', 'C', 'H', 'E', 'N', 0x0 }; /* Greek - "AlphaBetaGamma" */ const uint8_t srchost_utf8_lowcase[] = { 0xCE, 0xB1, 0xCE, 0xB2, 0xCE, 0xB3, 0x0 }; const uint8_t srchost_utf8_upcase[] = { 0xCE, 0x91, 0xCE, 0x92, 0xCE, 0x93, 0x0 }; /* Turkish "capital I" and "dotless i" */ const uint8_t user_lowcase_tr[] = { 0xC4, 0xB1, 0x0 }; const uint8_t user_upcase_tr[] = { 0x49, 0x0 }; static void get_allow_all_rule(TALLOC_CTX *mem_ctx, struct hbac_rule **allow_rule) { struct hbac_rule *rule; /* Create a rule that ALLOWs all services, users and * remote hosts. */ rule = talloc_zero(mem_ctx, struct hbac_rule); fail_if (rule == NULL); rule->enabled = true; rule->services = talloc_zero(rule, struct hbac_rule_element); fail_if (rule->services == NULL); rule->services->category = HBAC_CATEGORY_ALL; rule->services->names = NULL; rule->services->groups = NULL; rule->users = talloc_zero(rule, struct hbac_rule_element); fail_if (rule->users == NULL); rule->users->category = HBAC_CATEGORY_ALL; rule->users->names = NULL; rule->users->groups = NULL; rule->targethosts = talloc_zero(rule, struct hbac_rule_element); fail_if (rule->targethosts == NULL); rule->targethosts->category = HBAC_CATEGORY_ALL; rule->targethosts->names = NULL; rule->targethosts->groups = NULL; rule->srchosts = talloc_zero(rule, struct hbac_rule_element); fail_if (rule->srchosts == NULL); rule->srchosts->category = HBAC_CATEGORY_ALL; rule->srchosts->names = NULL; rule->srchosts->groups = NULL; *allow_rule = rule; } static void get_test_user(TALLOC_CTX *mem_ctx, struct hbac_request_element **user) { struct hbac_request_element *new_user; new_user = talloc_zero(mem_ctx, struct hbac_request_element); fail_if (new_user == NULL); new_user->name = talloc_strdup(new_user, HBAC_TEST_USER); fail_if(new_user->name == NULL); new_user->groups = talloc_array(new_user, const char *, 3); fail_if(new_user->groups == NULL); new_user->groups[0] = talloc_strdup(new_user->groups, HBAC_TEST_GROUP1); fail_if(new_user->groups[0] == NULL); new_user->groups[1] = talloc_strdup(new_user->groups, HBAC_TEST_GROUP2); fail_if(new_user->groups[1] == NULL); new_user->groups[2] = NULL; *user = new_user; } static void get_test_service(TALLOC_CTX *mem_ctx, struct hbac_request_element **service) { struct hbac_request_element *new_service; new_service = talloc_zero(mem_ctx, struct hbac_request_element); fail_if (new_service == NULL); new_service->name = talloc_strdup(new_service, HBAC_TEST_SERVICE); fail_if(new_service->name == NULL); new_service->groups = talloc_array(new_service, const char *, 3); fail_if(new_service->groups == NULL); new_service->groups[0] = talloc_strdup(new_service->groups, HBAC_TEST_SERVICEGROUP1); fail_if(new_service->groups[0] == NULL); new_service->groups[1] = talloc_strdup(new_service->groups, HBAC_TEST_SERVICEGROUP2); fail_if(new_service->groups[1] == NULL); new_service->groups[2] = NULL; *service = new_service; } static void get_test_srchost(TALLOC_CTX *mem_ctx, struct hbac_request_element **srchost) { struct hbac_request_element *new_srchost; new_srchost = talloc_zero(mem_ctx, struct hbac_request_element); fail_if (new_srchost == NULL); new_srchost->name = talloc_strdup(new_srchost, HBAC_TEST_SRCHOST); fail_if(new_srchost->name == NULL); new_srchost->groups = talloc_array(new_srchost, const char *, 3); fail_if(new_srchost->groups == NULL); new_srchost->groups[0] = talloc_strdup(new_srchost->groups, HBAC_TEST_SRCHOSTGROUP1); fail_if(new_srchost->groups[0] == NULL); new_srchost->groups[1] = talloc_strdup(new_srchost->groups, HBAC_TEST_SRCHOSTGROUP2); fail_if(new_srchost->groups[1] == NULL); new_srchost->groups[2] = NULL; *srchost = new_srchost; } START_TEST(ipa_hbac_test_allow_all) { enum hbac_eval_result result; TALLOC_CTX *test_ctx; struct hbac_rule **rules; struct hbac_eval_req *eval_req; struct hbac_info *info = NULL; bool is_valid; uint32_t missing_attrs; test_ctx = talloc_new(global_talloc_context); /* Create a request */ eval_req = talloc_zero(test_ctx, struct hbac_eval_req); fail_if (eval_req == NULL); get_test_user(eval_req, &eval_req->user); get_test_service(eval_req, &eval_req->service); get_test_srchost(eval_req, &eval_req->srchost); /* Create the rules to evaluate against */ rules = talloc_array(test_ctx, struct hbac_rule *, 2); fail_if (rules == NULL); get_allow_all_rule(rules, &rules[0]); rules[0]->name = talloc_strdup(rules[0], "Allow All"); fail_if(rules[0]->name == NULL); rules[1] = NULL; /* Validate this rule */ is_valid = hbac_rule_is_complete(rules[0], &missing_attrs); fail_unless(is_valid); fail_unless(missing_attrs == 0); /* Evaluate the rules */ result = hbac_evaluate(rules, eval_req, &info); fail_unless(result == HBAC_EVAL_ALLOW, "Expected [%s], got [%s]; " "Error: [%s]", hbac_result_string(HBAC_EVAL_ALLOW), hbac_result_string(result), info ? hbac_error_string(info->code):"Unknown"); hbac_free_info(info); info = NULL; talloc_free(test_ctx); } END_TEST START_TEST(ipa_hbac_test_allow_user) { enum hbac_eval_result result; TALLOC_CTX *test_ctx; struct hbac_rule **rules; struct hbac_eval_req *eval_req; struct hbac_info *info = NULL; bool is_valid; uint32_t missing_attrs; test_ctx = talloc_new(global_talloc_context); /* Create a request */ eval_req = talloc_zero(test_ctx, struct hbac_eval_req); fail_if (eval_req == NULL); get_test_user(eval_req, &eval_req->user); get_test_service(eval_req, &eval_req->service); get_test_srchost(eval_req, &eval_req->srchost); /* Create the rules to evaluate against */ rules = talloc_array(test_ctx, struct hbac_rule *, 2); fail_if (rules == NULL); get_allow_all_rule(rules, &rules[0]); /* Modify the rule to allow only a specific user */ rules[0]->name = talloc_strdup(rules[0], "Allow user"); fail_if(rules[0]->name == NULL); rules[0]->users->category = HBAC_CATEGORY_NULL; rules[0]->users->names = talloc_array(rules[0], const char *, 2); fail_if(rules[0]->users->names == NULL); rules[0]->users->names[0] = HBAC_TEST_USER; rules[0]->users->names[1] = NULL; rules[1] = NULL; /* Validate this rule */ is_valid = hbac_rule_is_complete(rules[0], &missing_attrs); fail_unless(is_valid); fail_unless(missing_attrs == 0); /* Evaluate the rules */ result = hbac_evaluate(rules, eval_req, &info); fail_unless(result == HBAC_EVAL_ALLOW, "Expected [%s], got [%s]; " "Error: [%s]", hbac_result_string(HBAC_EVAL_ALLOW), hbac_result_string(result), info ? hbac_error_string(info->code):"Unknown"); hbac_free_info(info); info = NULL; /* Negative test */ rules[0]->users->names[0] = HBAC_TEST_INVALID_USER; /* Validate this rule */ is_valid = hbac_rule_is_complete(rules[0], &missing_attrs); fail_unless(is_valid); fail_unless(missing_attrs == 0); /* Evaluate the rules */ result = hbac_evaluate(rules, eval_req, &info); fail_unless(result == HBAC_EVAL_DENY, "Expected [%s], got [%s]; " "Error: [%s]", hbac_result_string(HBAC_EVAL_DENY), hbac_result_string(result), info ? hbac_error_string(info->code):"Unknown"); hbac_free_info(info); info = NULL; talloc_free(test_ctx); } END_TEST START_TEST(ipa_hbac_test_allow_utf8) { enum hbac_eval_result result; TALLOC_CTX *test_ctx; struct hbac_rule **rules; struct hbac_eval_req *eval_req; struct hbac_info *info = NULL; bool is_valid; uint32_t missing_attrs; test_ctx = talloc_new(global_talloc_context); /* Create a request */ eval_req = talloc_zero(test_ctx, struct hbac_eval_req); fail_if (eval_req == NULL); get_test_user(eval_req, &eval_req->user); get_test_service(eval_req, &eval_req->service); get_test_srchost(eval_req, &eval_req->srchost); /* Override the with UTF8 values */ eval_req->user->name = (const char *) &user_utf8_lowcase; eval_req->srchost->name = (const char *) &srchost_utf8_lowcase; eval_req->service->name = (const char *) &service_utf8_lowcase; /* Create the rules to evaluate against */ rules = talloc_array(test_ctx, struct hbac_rule *, 2); fail_if (rules == NULL); get_allow_all_rule(rules, &rules[0]); rules[0]->name = talloc_strdup(rules[0], "Allow user"); fail_if(rules[0]->name == NULL); rules[0]->users->category = HBAC_CATEGORY_NULL; /* Modify the rule to allow only a specific user */ rules[0]->users->names = talloc_array(rules[0], const char *, 2); fail_if(rules[0]->users->names == NULL); rules[0]->users->names[0] = (const char *) &user_utf8_upcase; rules[0]->users->names[1] = NULL; /* Modify the rule to allow only a specific service */ rules[0]->services->category = HBAC_CATEGORY_NULL; rules[0]->services->names = talloc_array(rules[0], const char *, 2); fail_if(rules[0]->services->names == NULL); rules[0]->services->names[0] = (const char *) &service_utf8_upcase; rules[0]->services->names[1] = NULL; /* Modify the rule to allow only a specific service */ rules[0]->srchosts->category = HBAC_CATEGORY_NULL; rules[0]->srchosts->names = talloc_array(rules[0], const char *, 2); fail_if(rules[0]->services->names == NULL); rules[0]->srchosts->names[0] = (const char *) &srchost_utf8_upcase; rules[0]->services->names[1] = NULL; rules[1] = NULL; /* Validate this rule */ is_valid = hbac_rule_is_complete(rules[0], &missing_attrs); fail_unless(is_valid); fail_unless(missing_attrs == 0); /* Evaluate the rules */ result = hbac_evaluate(rules, eval_req, &info); fail_unless(result == HBAC_EVAL_ALLOW, "Expected [%s], got [%s]; " "Error: [%s]", hbac_result_string(HBAC_EVAL_ALLOW), hbac_result_string(result), info ? hbac_error_string(info->code):"Unknown"); hbac_free_info(info); info = NULL; /* Negative test - a different letter */ rules[0]->users->names[0] = (const char *) &user_utf8_lowcase_neg; /* Evaluate the rules */ result = hbac_evaluate(rules, eval_req, &info); fail_unless(result == HBAC_EVAL_DENY, "Expected [%s], got [%s]; " "Error: [%s]", hbac_result_string(HBAC_EVAL_DENY), hbac_result_string(result), info ? hbac_error_string(info->code):"Unknown"); hbac_free_info(info); info = NULL; /* Negative test - Turkish dotless i. We cannot know that capital I * casefolds into dotless i unless we know the language is Turkish */ eval_req->user->name = (const char *) &user_lowcase_tr; rules[0]->users->names[0] = (const char *) &user_upcase_tr; /* Validate this rule */ is_valid = hbac_rule_is_complete(rules[0], &missing_attrs); fail_unless(is_valid); fail_unless(missing_attrs == 0); /* Evaluate the rules */ result = hbac_evaluate(rules, eval_req, &info); fail_unless(result == HBAC_EVAL_DENY, "Expected [%s], got [%s]; " "Error: [%s]", hbac_result_string(HBAC_EVAL_DENY), hbac_result_string(result), info ? hbac_error_string(info->code):"Unknown"); hbac_free_info(info); info = NULL; talloc_free(test_ctx); } END_TEST START_TEST(ipa_hbac_test_allow_group) { enum hbac_eval_result result; TALLOC_CTX *test_ctx; struct hbac_rule **rules; struct hbac_eval_req *eval_req; struct hbac_info *info = NULL; bool is_valid; uint32_t missing_attrs; test_ctx = talloc_new(global_talloc_context); /* Create a request */ eval_req = talloc_zero(test_ctx, struct hbac_eval_req); fail_if (eval_req == NULL); get_test_user(eval_req, &eval_req->user); get_test_service(eval_req, &eval_req->service); get_test_srchost(eval_req, &eval_req->srchost); /* Create the rules to evaluate against */ rules = talloc_array(test_ctx, struct hbac_rule *, 2); fail_if (rules == NULL); get_allow_all_rule(rules, &rules[0]); /* Modify the rule to allow only a group of users */ rules[0]->name = talloc_strdup(rules[0], "Allow group"); fail_if(rules[0]->name == NULL); rules[0]->users->category = HBAC_CATEGORY_NULL; rules[0]->users->names = NULL; rules[0]->users->groups = talloc_array(rules[0], const char *, 2); fail_if(rules[0]->users->groups == NULL); rules[0]->users->groups[0] = HBAC_TEST_GROUP1; rules[0]->users->groups[1] = NULL; rules[1] = NULL; /* Validate this rule */ is_valid = hbac_rule_is_complete(rules[0], &missing_attrs); fail_unless(is_valid); fail_unless(missing_attrs == 0); /* Evaluate the rules */ result = hbac_evaluate(rules, eval_req, &info); fail_unless(result == HBAC_EVAL_ALLOW, "Expected [%s], got [%s]; " "Error: [%s]", hbac_result_string(HBAC_EVAL_ALLOW), hbac_result_string(result), info ? hbac_error_string(info->code):"Unknown"); hbac_free_info(info); info = NULL; /* Negative test */ rules[0]->users->groups[0] = HBAC_TEST_INVALID_GROUP; /* Validate this rule */ is_valid = hbac_rule_is_complete(rules[0], &missing_attrs); fail_unless(is_valid); fail_unless(missing_attrs == 0); /* Evaluate the rules */ result = hbac_evaluate(rules, eval_req, &info); fail_unless(result == HBAC_EVAL_DENY, "Expected [%s], got [%s]; " "Error: [%s]", hbac_result_string(HBAC_EVAL_DENY), hbac_result_string(result), info ? hbac_error_string(info->code):"Unknown"); hbac_free_info(info); info = NULL; talloc_free(test_ctx); } END_TEST START_TEST(ipa_hbac_test_allow_svc) { enum hbac_eval_result result; TALLOC_CTX *test_ctx; struct hbac_rule **rules; struct hbac_eval_req *eval_req; struct hbac_info *info = NULL; bool is_valid; uint32_t missing_attrs; test_ctx = talloc_new(global_talloc_context); /* Create a request */ eval_req = talloc_zero(test_ctx, struct hbac_eval_req); fail_if (eval_req == NULL); get_test_user(eval_req, &eval_req->user); get_test_service(eval_req, &eval_req->service); get_test_srchost(eval_req, &eval_req->srchost); /* Create the rules to evaluate against */ rules = talloc_array(test_ctx, struct hbac_rule *, 2); fail_if (rules == NULL); get_allow_all_rule(rules, &rules[0]); /* Modify the rule to allow only a specific service */ rules[0]->name = talloc_strdup(rules[0], "Allow service"); fail_if(rules[0]->name == NULL); rules[0]->services->category = HBAC_CATEGORY_NULL; rules[0]->services->names = talloc_array(rules[0], const char *, 2); fail_if(rules[0]->services->names == NULL); rules[0]->services->names[0] = HBAC_TEST_SERVICE; rules[0]->services->names[1] = NULL; rules[1] = NULL; /* Validate this rule */ is_valid = hbac_rule_is_complete(rules[0], &missing_attrs); fail_unless(is_valid); fail_unless(missing_attrs == 0); /* Evaluate the rules */ result = hbac_evaluate(rules, eval_req, &info); fail_unless(result == HBAC_EVAL_ALLOW, "Expected [%s], got [%s]; " "Error: [%s]", hbac_result_string(HBAC_EVAL_ALLOW), hbac_result_string(result), info ? hbac_error_string(info->code):"Unknown"); hbac_free_info(info); info = NULL; /* Negative test */ rules[0]->services->names[0] = HBAC_TEST_INVALID_SERVICE; /* Validate this rule */ is_valid = hbac_rule_is_complete(rules[0], &missing_attrs); fail_unless(is_valid); fail_unless(missing_attrs == 0); /* Evaluate the rules */ result = hbac_evaluate(rules, eval_req, &info); fail_unless(result == HBAC_EVAL_DENY, "Expected [%s], got [%s]; " "Error: [%s]", hbac_result_string(HBAC_EVAL_DENY), hbac_result_string(result), info ? hbac_error_string(info->code):"Unknown"); hbac_free_info(info); info = NULL; talloc_free(test_ctx); } END_TEST START_TEST(ipa_hbac_test_allow_svcgroup) { enum hbac_eval_result result; TALLOC_CTX *test_ctx; struct hbac_rule **rules; struct hbac_eval_req *eval_req; struct hbac_info *info = NULL; bool is_valid; uint32_t missing_attrs; test_ctx = talloc_new(global_talloc_context); /* Create a request */ eval_req = talloc_zero(test_ctx, struct hbac_eval_req); fail_if (eval_req == NULL); get_test_user(eval_req, &eval_req->user); get_test_service(eval_req, &eval_req->service); get_test_srchost(eval_req, &eval_req->srchost); /* Create the rules to evaluate against */ rules = talloc_array(test_ctx, struct hbac_rule *, 2); fail_if (rules == NULL); get_allow_all_rule(rules, &rules[0]); /* Modify the rule to allow only a group of users */ rules[0]->name = talloc_strdup(rules[0], "Allow servicegroup"); fail_if(rules[0]->name == NULL); rules[0]->services->category = HBAC_CATEGORY_NULL; rules[0]->services->names = NULL; rules[0]->services->groups = talloc_array(rules[0], const char *, 2); fail_if(rules[0]->services->groups == NULL); rules[0]->services->groups[0] = HBAC_TEST_SERVICEGROUP1; rules[0]->services->groups[1] = NULL; rules[1] = NULL; /* Validate this rule */ is_valid = hbac_rule_is_complete(rules[0], &missing_attrs); fail_unless(is_valid); fail_unless(missing_attrs == 0); /* Evaluate the rules */ result = hbac_evaluate(rules, eval_req, &info); fail_unless(result == HBAC_EVAL_ALLOW, "Expected [%s], got [%s]; " "Error: [%s]", hbac_result_string(HBAC_EVAL_ALLOW), hbac_result_string(result), info ? hbac_error_string(info->code):"Unknown"); hbac_free_info(info); info = NULL; /* Negative test */ rules[0]->services->groups[0] = HBAC_TEST_INVALID_SERVICEGROUP; /* Validate this rule */ is_valid = hbac_rule_is_complete(rules[0], &missing_attrs); fail_unless(is_valid); fail_unless(missing_attrs == 0); /* Evaluate the rules */ result = hbac_evaluate(rules, eval_req, &info); fail_unless(result == HBAC_EVAL_DENY, "Expected [%s], got [%s]; " "Error: [%s]", hbac_result_string(HBAC_EVAL_DENY), hbac_result_string(result), info ? hbac_error_string(info->code):"Unknown"); hbac_free_info(info); info = NULL; talloc_free(test_ctx); } END_TEST START_TEST(ipa_hbac_test_allow_srchost) { enum hbac_eval_result result; TALLOC_CTX *test_ctx; struct hbac_rule **rules; struct hbac_eval_req *eval_req; struct hbac_info *info = NULL; bool is_valid; uint32_t missing_attrs; test_ctx = talloc_new(global_talloc_context); /* Create a request */ eval_req = talloc_zero(test_ctx, struct hbac_eval_req); fail_if (eval_req == NULL); get_test_user(eval_req, &eval_req->user); get_test_service(eval_req, &eval_req->service); get_test_srchost(eval_req, &eval_req->srchost); /* Create the rules to evaluate against */ rules = talloc_array(test_ctx, struct hbac_rule *, 2); fail_if (rules == NULL); get_allow_all_rule(rules, &rules[0]); /* Modify the rule to allow only a specific service */ rules[0]->name = talloc_strdup(rules[0], "Allow srchost"); fail_if(rules[0]->name == NULL); rules[0]->srchosts->category = HBAC_CATEGORY_NULL; rules[0]->srchosts->names = talloc_array(rules[0], const char *, 2); fail_if(rules[0]->srchosts->names == NULL); rules[0]->srchosts->names[0] = HBAC_TEST_SRCHOST; rules[0]->srchosts->names[1] = NULL; rules[1] = NULL; /* Validate this rule */ is_valid = hbac_rule_is_complete(rules[0], &missing_attrs); fail_unless(is_valid); fail_unless(missing_attrs == 0); /* Evaluate the rules */ result = hbac_evaluate(rules, eval_req, &info); fail_unless(result == HBAC_EVAL_ALLOW, "Expected [%s], got [%s]; " "Error: [%s]", hbac_result_string(HBAC_EVAL_ALLOW), hbac_result_string(result), info ? hbac_error_string(info->code):"Unknown"); hbac_free_info(info); info = NULL; /* Negative test */ rules[0]->srchosts->names[0] = HBAC_TEST_INVALID_SRCHOST; /* Validate this rule */ is_valid = hbac_rule_is_complete(rules[0], &missing_attrs); fail_unless(is_valid); fail_unless(missing_attrs == 0); /* Evaluate the rules */ result = hbac_evaluate(rules, eval_req, &info); fail_unless(result == HBAC_EVAL_DENY, "Expected [%s], got [%s]; " "Error: [%s]", hbac_result_string(HBAC_EVAL_DENY), hbac_result_string(result), info ? hbac_error_string(info->code):"Unknown"); hbac_free_info(info); info = NULL; talloc_free(test_ctx); } END_TEST START_TEST(ipa_hbac_test_allow_srchostgroup) { enum hbac_eval_result result; TALLOC_CTX *test_ctx; struct hbac_rule **rules; struct hbac_eval_req *eval_req; struct hbac_info *info = NULL; bool is_valid; uint32_t missing_attrs; test_ctx = talloc_new(global_talloc_context); /* Create a request */ eval_req = talloc_zero(test_ctx, struct hbac_eval_req); fail_if (eval_req == NULL); get_test_user(eval_req, &eval_req->user); get_test_service(eval_req, &eval_req->service); get_test_srchost(eval_req, &eval_req->srchost); /* Create the rules to evaluate against */ rules = talloc_array(test_ctx, struct hbac_rule *, 2); fail_if (rules == NULL); get_allow_all_rule(rules, &rules[0]); /* Modify the rule to allow only a group of users */ rules[0]->name = talloc_strdup(rules[0], "Allow srchostgroup"); fail_if(rules[0]->name == NULL); rules[0]->srchosts->category = HBAC_CATEGORY_NULL; rules[0]->srchosts->names = NULL; rules[0]->srchosts->groups = talloc_array(rules[0], const char *, 2); fail_if(rules[0]->srchosts->groups == NULL); rules[0]->srchosts->groups[0] = HBAC_TEST_SRCHOSTGROUP1; rules[0]->srchosts->groups[1] = NULL; rules[1] = NULL; /* Validate this rule */ is_valid = hbac_rule_is_complete(rules[0], &missing_attrs); fail_unless(is_valid); fail_unless(missing_attrs == 0); /* Evaluate the rules */ result = hbac_evaluate(rules, eval_req, &info); fail_unless(result == HBAC_EVAL_ALLOW, "Expected [%s], got [%s]; " "Error: [%s]", hbac_result_string(HBAC_EVAL_ALLOW), hbac_result_string(result), info ? hbac_error_string(info->code):"Unknown"); hbac_free_info(info); info = NULL; /* Negative test */ rules[0]->srchosts->groups[0] = HBAC_TEST_INVALID_SRCHOSTGROUP; /* Validate this rule */ is_valid = hbac_rule_is_complete(rules[0], &missing_attrs); fail_unless(is_valid); fail_unless(missing_attrs == 0); /* Evaluate the rules */ result = hbac_evaluate(rules, eval_req, &info); fail_unless(result == HBAC_EVAL_DENY, "Expected [%s], got [%s]; " "Error: [%s]", hbac_result_string(HBAC_EVAL_DENY), hbac_result_string(result), info ? hbac_error_string(info->code):"Unknown"); hbac_free_info(info); info = NULL; talloc_free(test_ctx); } END_TEST START_TEST(ipa_hbac_test_incomplete) { TALLOC_CTX *test_ctx; struct hbac_rule *rule; bool is_valid; uint32_t missing_attrs; test_ctx = talloc_new(global_talloc_context); rule = talloc_zero(test_ctx, struct hbac_rule); /* Validate this rule */ is_valid = hbac_rule_is_complete(rule, &missing_attrs); fail_if(is_valid); fail_unless(missing_attrs | HBAC_RULE_ELEMENT_USERS); fail_unless(missing_attrs | HBAC_RULE_ELEMENT_SERVICES); fail_unless(missing_attrs | HBAC_RULE_ELEMENT_TARGETHOSTS); fail_unless(missing_attrs | HBAC_RULE_ELEMENT_SOURCEHOSTS); talloc_free(test_ctx); } END_TEST Suite *hbac_test_suite (void) { Suite *s = suite_create ("HBAC"); TCase *tc_hbac = tcase_create("HBAC_rules"); tcase_add_checked_fixture(tc_hbac, ck_leak_check_setup, ck_leak_check_teardown); tcase_add_test(tc_hbac, ipa_hbac_test_allow_all); tcase_add_test(tc_hbac, ipa_hbac_test_allow_user); tcase_add_test(tc_hbac, ipa_hbac_test_allow_group); tcase_add_test(tc_hbac, ipa_hbac_test_allow_svc); tcase_add_test(tc_hbac, ipa_hbac_test_allow_svcgroup); tcase_add_test(tc_hbac, ipa_hbac_test_allow_srchost); tcase_add_test(tc_hbac, ipa_hbac_test_allow_srchostgroup); tcase_add_test(tc_hbac, ipa_hbac_test_allow_utf8); tcase_add_test(tc_hbac, ipa_hbac_test_incomplete); suite_add_tcase(s, tc_hbac); return s; } int main(int argc, const char *argv[]) { int number_failed; tests_set_cwd(); Suite *s = hbac_test_suite(); SRunner *sr = srunner_create(s); /* If CK_VERBOSITY is set, use that, otherwise it defaults to CK_NORMAL */ srunner_run_all(sr, CK_ENV); number_failed = srunner_ntests_failed (sr); srunner_free (sr); return (number_failed == 0) ? EXIT_SUCCESS : EXIT_FAILURE; }