diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml index cf7cacc..4f0053c 100644 --- a/.gitlab-ci.yml +++ b/.gitlab-ci.yml @@ -24,8 +24,9 @@ run_unit_test: when: always paths: - timestamp.log + - memory-report.xml - unit-test-coverage.xml - + run_api_test: stage: api_test image: iopsys/code-analysis:latest diff --git a/bin/Makefile.am b/bin/Makefile.am index f077a07..d250ea8 100755 --- a/bin/Makefile.am +++ b/bin/Makefile.am @@ -98,6 +98,6 @@ libicwmp_la_SOURCES = \ ../diagnostic.c \ ../reboot.c -libicwmp_la_CFLAGS=-I../inc +libicwmp_la_CFLAGS=-g -I../inc libicwmp_la_LDFLAGS= $(AM_LIBS) -luci -lubox -lubus $(MICROXML_LIBS) $(LIBCURL_LIBS) -lpthread -lcrypto -lssl -ljson-c -lblobmsg_json -lz -lm endif diff --git a/inc/xml.h b/inc/xml.h index cd31c9c..f66f598 100644 --- a/inc/xml.h +++ b/inc/xml.h @@ -21,12 +21,12 @@ #define CWMP_MXML_TAB_SPACE " " #define MAX_SCHEDULE_INFORM_QUEUE 10 -#define MXML_DELETE(X) \ - do { \ - if (X) { \ - mxmlDelete(X); \ - X = NULL; \ - } \ +#define MXML_DELETE(X) \ + do { \ + if (X) { \ + mxmlDelete(X); \ + X = NULL; \ + } \ } while (0) extern const struct rpc_cpe_method rpc_cpe_methods[__RPC_CPE_MAX]; @@ -66,6 +66,7 @@ int xml_prepare_msg_out(struct session *session); int xml_prepare_lwnotification_message(char **msg_out); int xml_set_cwmp_id_rpc_cpe(struct session *session); int cwmp_create_fault_message(struct session *session, struct rpc *rpc_cpe, int fault_code); +int xml_recreate_namespace(mxml_node_t *tree); const char *whitespace_cb(mxml_node_t *node, int where); int xml_set_cwmp_id(struct session *session); diff --git a/session.c b/session.c index 75c5581..35dafde 100644 --- a/session.c +++ b/session.c @@ -121,9 +121,10 @@ int cwmp_session_rpc_destructor(struct rpc *rpc) int cwmp_session_destructor(struct session *session) { struct rpc *rpc; - while (session->head_rpc_acs.next != &(session->head_rpc_acs)) { rpc = list_entry(session->head_rpc_acs.next, struct rpc, list); + if (!rpc) + break; if (rpc_acs_methods[rpc->type].extra_clean != NULL) rpc_acs_methods[rpc->type].extra_clean(session, rpc); cwmp_session_rpc_destructor(rpc); @@ -131,12 +132,13 @@ int cwmp_session_destructor(struct session *session) while (session->head_rpc_cpe.next != &(session->head_rpc_cpe)) { rpc = list_entry(session->head_rpc_cpe.next, struct rpc, list); + if (!rpc) + break; cwmp_session_rpc_destructor(rpc); } if (session->list.next != NULL && session->list.prev != NULL) list_del(&(session->list)); - free(session); return CWMP_OK; diff --git a/test/cmocka/Makefile b/test/cmocka/Makefile index 579935c..33fdeeb 100644 --- a/test/cmocka/Makefile +++ b/test/cmocka/Makefile @@ -1,15 +1,16 @@ CC = gcc -CFLAGS = -g -Wall -Werror +CFLAGS = -g -Wall -I./inc LDFLAGS = -lcmocka -licwmp -lmicroxml -UNIT_TESTS = unit_test_icwmpd +UNIT_TESTS = icwmp_datamodel_interface_unit_testd icwmp_soap_msg_unit_testd + +VALGRIND = valgrind --xml=yes --xml-file=/builds/iopsys/icwmp/memory-report.xml --leak-check=full --show-reachable=yes --show-leak-kinds=all --errors-for-leak-kinds=all + +icwmp_datamodel_interface_unit_testd: icwmp_datamodel_interface_unit_test.o + $(CC) -o $@ $^ $(LDFLAGS) $(CFLAGS) + +icwmp_soap_msg_unit_testd: icwmp_soap_msg_unit_test.o + $(CC) -o $@ $^ $(LDFLAGS) $(CFLAGS) -VALGRIND = valgrind --show-reachable=yes \ - --show-leak-kinds=all --errors-for-leak-kinds=all \ - --error-exitcode=1 --track-origins=yes - -unit_test_icwmpd: unit_test_icwmp.o - $(CC) -o $@ $^ $(LDFLAGS) - unit-test: $(UNIT_TESTS) $(foreach testprog, $(UNIT_TESTS), sudo $(VALGRIND) ./$(testprog);) diff --git a/test/cmocka/unit_test_icwmp.c b/test/cmocka/icwmp_datamodel_interface_unit_test.c similarity index 79% rename from test/cmocka/unit_test_icwmp.c rename to test/cmocka/icwmp_datamodel_interface_unit_test.c index fc1303d..5e07093 100755 --- a/test/cmocka/unit_test_icwmp.c +++ b/test/cmocka/icwmp_datamodel_interface_unit_test.c @@ -12,17 +12,7 @@ #include #include -struct cwmp cwmp_main_test = { 0 }; -struct cwmp *cwmp_test; - -static int group_setup(void **state) -{ - cwmp_test = &cwmp_main_test; - INIT_LIST_HEAD(&(cwmp_test->head_session_queue)); - return 0; -} - -static int group_teardown(void **state) +static int dm_iface_unit_tests_clean(void **state) { icwmp_cleanmem(); return 0; @@ -320,7 +310,7 @@ static void dm_get_parameter_names_test(void **state) assert_string_equal(fault, "9005"); } -static void dm_set_parameter_attributes_test(void **state) +void dm_set_parameter_attributes_test(void **state) { char *fault = NULL; @@ -398,76 +388,6 @@ static void dm_get_parameter_attributes_test(void **state) cwmp_free_all_dm_parameter_list(¶meters_list); } -/* - * SOAP TESTS - */ -static void get_config_test(void **state) -{ - struct cwmp *cwmp_test = &cwmp_main_test; - int error = get_global_config(&(cwmp_test->conf)); - assert_int_equal(error, CWMP_OK); -} - -static void get_deviceid_test(void **state) -{ - struct cwmp *cwmp_test = &cwmp_main_test; - int error = cwmp_get_deviceid(cwmp_test); - assert_int_equal(error, CWMP_OK); -} - -static void add_event_test(void **state) -{ - struct event_container *event_container; - event_container = cwmp_add_event_container(cwmp_test, EVENT_IDX_1BOOT, ""); - assert_non_null(event_container); - assert_string_equal(EVENT_CONST[event_container->code].CODE, "1 BOOT"); -} - -static void soap_inform_message_test(void **state) -{ - struct session *session; - mxml_node_t *env = NULL, *n = NULL, *device_id = NULL, *cwmp_inform = NULL; - - memcpy(&(cwmp_test->env), &cwmp_test, sizeof(struct env)); - session = calloc(1, sizeof(struct session)); - if (session == NULL) - return; - - list_add_tail(&(session->list), &(cwmp_test->head_session_queue)); - - INIT_LIST_HEAD(&(session->head_event_container)); - session = list_entry((&(cwmp_test->head_session_queue))->next, struct session, list); - struct rpc *rpc_acs; - rpc_acs = list_entry(&(session->head_rpc_acs), struct rpc, list); - - cwmp_rpc_acs_prepare_message_inform(cwmp_test, session, rpc_acs); - - env = mxmlFindElement(session->tree_out, session->tree_out, "soap_env:Envelope", NULL, NULL, MXML_DESCEND); - assert_non_null(env); - n = mxmlFindElement(env, env, "soap_env:Header", NULL, NULL, MXML_DESCEND); - assert_non_null(n); - n = mxmlFindElement(n, n, "cwmp:ID", NULL, NULL, MXML_DESCEND); - assert_non_null(n); - n = mxmlFindElement(env, env, "soap_env:Body", NULL, NULL, MXML_DESCEND); - assert_non_null(n); - cwmp_inform = mxmlFindElement(env, env, "cwmp:Inform", NULL, NULL, MXML_DESCEND); - assert_non_null(cwmp_inform); - device_id = mxmlFindElement(cwmp_inform, cwmp_inform, "DeviceId", NULL, NULL, MXML_DESCEND); - assert_non_null(device_id); - n = mxmlFindElement(device_id, device_id, "Manufacturer", NULL, NULL, MXML_DESCEND); - assert_non_null(n); - n = mxmlFindElement(device_id, device_id, "OUI", NULL, NULL, MXML_DESCEND); - assert_non_null(n); - n = mxmlFindElement(device_id, device_id, "ProductClass", NULL, NULL, MXML_DESCEND); - assert_non_null(n); - n = mxmlFindElement(device_id, device_id, "SerialNumber", NULL, NULL, MXML_DESCEND); - assert_non_null(n); - n = mxmlFindElement(cwmp_inform, cwmp_inform, "Event", NULL, NULL, MXML_DESCEND); - assert_non_null(n); - n = mxmlFindElement(cwmp_inform, cwmp_inform, "ParameterList", NULL, NULL, MXML_DESCEND); - assert_non_null(n); -} - int main(void) { const struct CMUnitTest tests[] = { @@ -478,11 +398,7 @@ int main(void) cmocka_unit_test(dm_get_parameter_names_test), cmocka_unit_test(dm_set_parameter_attributes_test), cmocka_unit_test(dm_get_parameter_attributes_test), - cmocka_unit_test(get_config_test), - cmocka_unit_test(get_deviceid_test), - cmocka_unit_test(add_event_test), - cmocka_unit_test(soap_inform_message_test), }; - return cmocka_run_group_tests(tests, group_setup, group_teardown); + return cmocka_run_group_tests(tests, NULL, dm_iface_unit_tests_clean); } diff --git a/test/cmocka/icwmp_soap_msg_unit_test.c b/test/cmocka/icwmp_soap_msg_unit_test.c new file mode 100644 index 0000000..1cf6da1 --- /dev/null +++ b/test/cmocka/icwmp_soap_msg_unit_test.c @@ -0,0 +1,1063 @@ +/* + * 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 2 of the License, or + * (at your option) any later version. + * + * Copyright (C) 2013-2020 iopsys Software Solutions AB + * Author Omar Kallel + */ + +#include +#include +#include +#include +#include + +#include +#include +#include +#include +#include +#include +#include + +#include "icwmp_soap_msg_unit_test.h" + +struct cwmp cwmp_main_test = { 0 }; +struct cwmp *cwmp_test; +struct session *session_test = NULL; +int instance = 0; + +/* + * End test clean + */ +void clean_config() +{ + FREE(cwmp_test->deviceid.manufacturer); + FREE(cwmp_test->deviceid.serialnumber); + FREE(cwmp_test->deviceid.productclass); + FREE(cwmp_test->deviceid.oui); + FREE(cwmp_test->deviceid.softwareversion); + FREE(cwmp_test->conf.lw_notification_hostname); + FREE(cwmp_test->conf.ip); + FREE(cwmp_test->conf.ipv6); + FREE(cwmp_test->conf.acsurl); + FREE(cwmp_test->conf.acs_userid); + FREE(cwmp_test->conf.acs_passwd); + FREE(cwmp_test->conf.interface); + FREE(cwmp_test->conf.cpe_userid); + FREE(cwmp_test->conf.cpe_passwd); + FREE(cwmp_test->conf.ubus_socket); + FREE(cwmp_test->conf.connection_request_path); + FREE(cwmp_test->conf.default_wan_iface); +} + +void clean_name_space() +{ + FREE(ns.soap_env); + FREE(ns.soap_enc); + FREE(ns.xsd); + FREE(ns.xsi); + FREE(ns.cwmp); +} + +void unit_test_remove_all_events_by_session(struct session *session) +{ + struct event_container *event_container; + + while (session->head_event_container.next != &(session->head_event_container)) { + event_container = list_entry(session->head_event_container.next, struct event_container, list); + free(event_container->command_key); + cwmp_free_all_dm_parameter_list(&(event_container->head_dm_parameter)); + list_del(&(event_container->list)); + free(event_container); + } +} + +void unit_test_end_test_destruction() +{ + struct session *session = NULL; + while (cwmp_test->head_session_queue.next != &(cwmp_test->head_session_queue)) { + session = list_entry(cwmp_test->head_session_queue.next, struct session, list); + unit_test_remove_all_events_by_session(session); + cwmp_session_destructor(session); + } +} + +/* + * CMOCKA functions + */ +static int soap_unit_tests_init(void **state) +{ + cwmp_test = &cwmp_main_test; + INIT_LIST_HEAD(&(cwmp_test->head_session_queue)); + memcpy(&(cwmp_test->env), &cwmp_test, sizeof(struct env)); + return 0; +} + +static int soap_unit_tests_clean(void **state) +{ + icwmp_cleanmem(); + if (session_test != NULL) { + MXML_DELETE(session_test->tree_in); + MXML_DELETE(session_test->tree_out); + session_test->head_rpc_acs.next = NULL; + session_test->head_rpc_cpe.next = NULL; + cwmp_session_destructor(session_test); + } + icwmp_free_list_services(); + clean_name_space(); + clean_config(); + return 0; +} + +/* + * UNIT Tests + */ +static void get_config_test(void **state) +{ + struct cwmp *cwmp_test = &cwmp_main_test; + int error = get_global_config(&(cwmp_test->conf)); + assert_int_equal(error, CWMP_OK); + log_set_severity_idx("INFO"); +} + +static void get_deviceid_test(void **state) +{ + struct cwmp *cwmp_test = &cwmp_main_test; + int error = cwmp_get_deviceid(cwmp_test); + assert_int_equal(error, CWMP_OK); +} + +static void add_event_test(void **state) +{ + struct event_container *event_container; + event_container = cwmp_add_event_container(cwmp_test, EVENT_IDX_1BOOT, ""); + assert_non_null(event_container); + assert_string_equal(EVENT_CONST[event_container->code].CODE, "1 BOOT"); +} + +int create_session(struct session **session) +{ + *session = calloc(1, sizeof(struct session)); + if (*session == NULL) + return 0; + + list_add_tail(&((*session)->list), &(cwmp_test->head_session_queue)); + + INIT_LIST_HEAD(&((*session)->head_event_container)); + *session = list_entry((&(cwmp_test->head_session_queue))->next, struct session, list); + return 1; +} + +static void soap_inform_message_test(void **state) +{ + mxml_node_t *env = NULL, *n = NULL, *device_id = NULL, *cwmp_inform = NULL; + struct session *session = NULL; + struct rpc *rpc_acs; + + create_session(&session); + session_test = session; + rpc_acs = list_entry(&(session->head_rpc_acs), struct rpc, list); + + cwmp_rpc_acs_prepare_message_inform(cwmp_test, session, rpc_acs); + + env = mxmlFindElement(session->tree_out, session->tree_out, "soap_env:Envelope", NULL, NULL, MXML_DESCEND); + assert_non_null(env); + n = mxmlFindElement(env, env, "soap_env:Header", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "cwmp:ID", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(env, env, "soap_env:Body", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + cwmp_inform = mxmlFindElement(env, env, "cwmp:Inform", NULL, NULL, MXML_DESCEND); + assert_non_null(cwmp_inform); + device_id = mxmlFindElement(cwmp_inform, cwmp_inform, "DeviceId", NULL, NULL, MXML_DESCEND); + assert_non_null(device_id); + n = mxmlFindElement(device_id, device_id, "Manufacturer", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(device_id, device_id, "OUI", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(device_id, device_id, "ProductClass", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(device_id, device_id, "SerialNumber", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(cwmp_inform, cwmp_inform, "Event", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "EventStruct", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "EventCode", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + assert_string_equal(n->child->value.opaque, "1 BOOT"); + n = mxmlFindElement(cwmp_inform, cwmp_inform, "ParameterList", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + + MXML_DELETE(session->tree_in); + MXML_DELETE(session->tree_out); + + unit_test_end_test_destruction(); + clean_config(); + session_test = NULL; +} + +static void prepare_session_for_rpc_method_call(struct session *session) +{ + mxml_node_t *b; + char *c; + + icwmp_asprintf(&c, "%s:%s", ns.soap_env, "Body"); + b = mxmlFindElement(session->tree_in, session->tree_in, c, NULL, NULL, MXML_DESCEND); + session->body_in = b; + xml_prepare_msg_out(session); +} + +static void prepare_gpv_soap_request(struct session *session, char *parameters[], int len) +{ + mxml_node_t *params = NULL, *n = NULL; + int i; + + session->tree_in = mxmlLoadString(NULL, CWMP_GETPARAMETERVALUES_REQ, MXML_OPAQUE_CALLBACK); + xml_recreate_namespace(session->tree_in); + params = mxmlFindElement(session->tree_in, session->tree_in, "ParameterNames", NULL, NULL, MXML_DESCEND); + for (i = 0; i < len; i++) { + n = mxmlNewElement(params, "string"); + n = mxmlNewOpaque(n, parameters[i]); + } +} + +static void soap_get_param_value_message_test(void **state) +{ + struct session *session = NULL; + mxml_node_t *env = NULL, *n = NULL, *name = NULL, *value = NULL; + struct rpc *rpc_cpe; + + create_session(&session); + session_test = session; + + rpc_cpe = list_entry(&(session->head_rpc_cpe), struct rpc, list); + + /* + * Valid parameter path + */ + char *valid_parameters[1] = { "Device.ManagementServer.PeriodicInformEnable" }; + prepare_gpv_soap_request(session, valid_parameters, 1); + + prepare_session_for_rpc_method_call(session); + + int ret = cwmp_handle_rpc_cpe_get_parameter_values(session, rpc_cpe); + assert_int_equal(ret, 0); + + env = mxmlFindElement(session->tree_out, session->tree_out, "soap_env:Envelope", NULL, NULL, MXML_DESCEND); + assert_non_null(env); + n = mxmlFindElement(env, env, "soap_env:Header", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "cwmp:ID", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(env, env, "soap_env:Body", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "cwmp:GetParameterValuesResponse", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "ParameterList", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "ParameterValueStruct", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + + name = mxmlFindElement(n, n, "Name", NULL, NULL, MXML_DESCEND); + assert_non_null(name); + assert_string_equal(name->child->value.opaque, "Device.ManagementServer.PeriodicInformEnable"); + value = mxmlFindElement(n, n, "Value", NULL, NULL, MXML_DESCEND); + assert_non_null(value); + + MXML_DELETE(session->tree_in); + MXML_DELETE(session->tree_out); + + /* + * Wrong parameter path + */ + mxml_node_t *fault_code = NULL, *fault_string = NULL, *detail = NULL, *detail_code = NULL, *detail_string = NULL; + + char *invalid_parameter[1] = { "Device.ManagementServereriodicInformEnable" }; + prepare_gpv_soap_request(session, invalid_parameter, 1); + + prepare_session_for_rpc_method_call(session); + + ret = cwmp_handle_rpc_cpe_get_parameter_values(session, rpc_cpe); + assert_int_equal(ret, 0); + + env = mxmlFindElement(session->tree_out, session->tree_out, "soap_env:Envelope", NULL, NULL, MXML_DESCEND); + assert_non_null(env); + n = mxmlFindElement(env, env, "soap_env:Header", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "cwmp:ID", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(env, env, "soap_env:Body", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "soap_env:Fault", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + fault_code = mxmlFindElement(n, n, "faultcode", NULL, NULL, MXML_DESCEND); + assert_non_null(fault_code); + fault_string = mxmlFindElement(n, n, "faultstring", NULL, NULL, MXML_DESCEND); + assert_non_null(fault_string); + detail = mxmlFindElement(n, n, "detail", NULL, NULL, MXML_DESCEND); + assert_non_null(detail); + detail = mxmlFindElement(detail, detail, "cwmp:Fault", NULL, NULL, MXML_DESCEND); + assert_non_null(detail); + detail_code = mxmlFindElement(detail, detail, "FaultCode", NULL, NULL, MXML_DESCEND); + assert_non_null(detail_code); + assert_string_equal(detail_code->child->value.opaque, "9005"); + detail_string = mxmlFindElement(detail, detail, "FaultString", NULL, NULL, MXML_DESCEND); + assert_non_null(detail_string); + + MXML_DELETE(session->tree_in); + MXML_DELETE(session->tree_out); + session->head_rpc_acs.next = NULL; + + unit_test_end_test_destruction(); + clean_name_space(); + session_test = NULL; +} + +/*static void prepare_spv_soap_request(struct session *session, char *parameter, char *value) +{ + mxml_node_t *params = NULL, *n = NULL; + + session->tree_in = mxmlLoadString(NULL, CWMP_SETPARAMETERVALUES_REQ, MXML_OPAQUE_CALLBACK); + xml_recreate_namespace(session->tree_in); + params = mxmlFindElement(session->tree_in, session->tree_in, "ParameterValueStruct", NULL, NULL, MXML_DESCEND); + n = mxmlNewElement(params, "Name"); + n = mxmlNewOpaque(n, parameter); + n = mxmlNewElement(params, "Value"); + mxmlElementSetAttr(n, "xsi:type", "xsd:string"); + n = mxmlNewOpaque(n, value); +} + +static void soap_set_param_value_message_test(void **state) +{ + struct session *session = NULL; + mxml_node_t *env = NULL, *n = NULL; + struct rpc *rpc_cpe; + + create_session(&session); + session_test = session; + + rpc_cpe = list_entry(&(session->head_rpc_cpe), struct rpc, list); + + + * Valid path & writable parameter + + rpc_cpe->type = RPC_CPE_SET_PARAMETER_VALUES; + prepare_spv_soap_request(session, "Device.ManagementServer.PeriodicInformEnable", "true"); + prepare_session_for_rpc_method_call(session); + + int ret = cwmp_handle_rpc_cpe_set_parameter_values(session, rpc_cpe); + assert_int_equal(ret, 0); + + env = mxmlFindElement(session->tree_out, session->tree_out, "soap_env:Envelope", NULL, NULL, MXML_DESCEND); + assert_non_null(env); + n = mxmlFindElement(env, env, "soap_env:Header", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "cwmp:ID", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(env, env, "soap_env:Body", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "cwmp:SetParameterValuesResponse", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "Status", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + assert_string_equal(n->child->value.opaque, "1"); + + rpc_cpe->list_set_value_fault = NULL; + MXML_DELETE(session->tree_in); + MXML_DELETE(session->tree_out); + session->tree_out = NULL; + + + * Wrong parameter path + + rpc_cpe->type = RPC_CPE_SET_PARAMETER_VALUES; + mxml_node_t *cwmp_fault = NULL, *set_val_fault = NULL; + + prepare_spv_soap_request(session, "Device.ManagementServeriodicInformEnable", "mngmt_enable"); + prepare_session_for_rpc_method_call(session); + + ret = cwmp_handle_rpc_cpe_set_parameter_values(session, rpc_cpe); + assert_int_equal(ret, 0); + + env = mxmlFindElement(session->tree_out, session->tree_out, "soap_env:Envelope", NULL, NULL, MXML_DESCEND); + assert_non_null(env); + n = mxmlFindElement(env, env, "soap_env:Header", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "cwmp:ID", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(env, env, "soap_env:Body", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(env, env, "soap_env:Fault", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "detail", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + cwmp_fault = mxmlFindElement(n, n, "cwmp:Fault", NULL, NULL, MXML_DESCEND); + assert_non_null(cwmp_fault); + n = mxmlFindElement(cwmp_fault, cwmp_fault, "FaultCode", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + assert_string_equal(n->child->value.opaque, "9003"); + n = mxmlFindElement(cwmp_fault, cwmp_fault, "FaultString", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + set_val_fault = mxmlFindElement(cwmp_fault, cwmp_fault, "SetParameterValuesFault", NULL, NULL, MXML_DESCEND); + assert_non_null(set_val_fault); + n = mxmlFindElement(set_val_fault, set_val_fault, "ParameterName", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + assert_string_equal(n->child->value.opaque, "Device.ManagementServeriodicInformEnable"); + n = mxmlFindElement(set_val_fault, set_val_fault, "FaultCode", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + assert_string_equal(n->child->value.opaque, "9005"); + n = mxmlFindElement(set_val_fault, set_val_fault, "FaultString", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + rpc_cpe->list_set_value_fault = NULL; + MXML_DELETE(session->tree_in); + MXML_DELETE(session->tree_out); + session->tree_in = NULL; + session->tree_out = NULL; + + + * Not writable & Valid parameter path + + rpc_cpe->type = RPC_CPE_SET_PARAMETER_VALUES; + prepare_spv_soap_request(session, "Device.ManagementServer.AliasBasedAddressing", "true"); + prepare_session_for_rpc_method_call(session); + + ret = cwmp_handle_rpc_cpe_set_parameter_values(session, rpc_cpe); + assert_int_equal(ret, 0); + + env = mxmlFindElement(session->tree_out, session->tree_out, "soap_env:Envelope", NULL, NULL, MXML_DESCEND); + assert_non_null(env); + n = mxmlFindElement(env, env, "soap_env:Header", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "cwmp:ID", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(env, env, "soap_env:Body", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(env, env, "soap_env:Fault", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "detail", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + cwmp_fault = mxmlFindElement(n, n, "cwmp:Fault", NULL, NULL, MXML_DESCEND); + assert_non_null(cwmp_fault); + n = mxmlFindElement(cwmp_fault, cwmp_fault, "FaultCode", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + assert_string_equal(n->child->value.opaque, "9003"); + n = mxmlFindElement(cwmp_fault, cwmp_fault, "FaultString", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + set_val_fault = mxmlFindElement(cwmp_fault, cwmp_fault, "SetParameterValuesFault", NULL, NULL, MXML_DESCEND); + assert_non_null(set_val_fault); + n = mxmlFindElement(set_val_fault, set_val_fault, "ParameterName", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + assert_string_equal(n->child->value.opaque, "Device.ManagementServer.AliasBasedAddressing"); + n = mxmlFindElement(set_val_fault, set_val_fault, "FaultCode", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + assert_string_equal(n->child->value.opaque, "9008"); + n = mxmlFindElement(set_val_fault, set_val_fault, "FaultString", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + rpc_cpe->list_set_value_fault = NULL; + MXML_DELETE(session->tree_in); + MXML_DELETE(session->tree_out); + + session->head_rpc_acs.next = NULL; + unit_test_end_test_destruction(); + clean_name_space(); + session_test = NULL; +}*/ + +static void prepare_addobj_soap_request(struct session *session, char *object) +{ + mxml_node_t *n = NULL; + + session->tree_in = mxmlLoadString(NULL, CWMP_ADDOBJECT_REQ, MXML_OPAQUE_CALLBACK); + xml_recreate_namespace(session->tree_in); + n = mxmlFindElement(session->tree_in, session->tree_in, "cwmp:AddObject", NULL, NULL, MXML_DESCEND); + n = mxmlFindElement(n, n, "ObjectName", NULL, NULL, MXML_DESCEND); + n = mxmlNewOpaque(n, object); +} + +static void soap_add_object_message_test(void **state) +{ + struct session *session = NULL; + mxml_node_t *env = NULL, *n = NULL, *add_resp = NULL; + struct rpc *rpc_cpe; + + create_session(&session); + session_test = session; + rpc_cpe = list_entry(&(session->head_rpc_cpe), struct rpc, list); + + /* + * Valid path & writable object + */ + prepare_addobj_soap_request(session, "Device.WiFi.SSID."); + prepare_session_for_rpc_method_call(session); + + int ret = cwmp_handle_rpc_cpe_add_object(session, rpc_cpe); + assert_int_equal(ret, 0); + env = mxmlFindElement(session->tree_out, session->tree_out, "soap_env:Envelope", NULL, NULL, MXML_DESCEND); + assert_non_null(env); + n = mxmlFindElement(env, env, "soap_env:Header", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "cwmp:ID", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(env, env, "soap_env:Body", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + add_resp = mxmlFindElement(n, n, "cwmp:AddObjectResponse", NULL, NULL, MXML_DESCEND); + assert_non_null(add_resp); + n = mxmlFindElement(add_resp, add_resp, "InstanceNumber", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + instance = (n->child && n->child->value.opaque) ? atoi(n->child->value.opaque) : 1; + n = mxmlFindElement(add_resp, add_resp, "Status", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + assert_string_equal(n->child->value.opaque, "1"); + MXML_DELETE(session->tree_in); + MXML_DELETE(session->tree_out); + + /* + * Wrong object path + */ + mxml_node_t *cwmp_fault = NULL; + + prepare_addobj_soap_request(session, "Device.WiFi.SSI."); + prepare_session_for_rpc_method_call(session); + + ret = cwmp_handle_rpc_cpe_add_object(session, rpc_cpe); + assert_int_equal(ret, 0); + + env = mxmlFindElement(session->tree_out, session->tree_out, "soap_env:Envelope", NULL, NULL, MXML_DESCEND); + assert_non_null(env); + n = mxmlFindElement(env, env, "soap_env:Header", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "cwmp:ID", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(env, env, "soap_env:Body", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "soap_env:Fault", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "detail", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + cwmp_fault = mxmlFindElement(n, n, "cwmp:Fault", NULL, NULL, MXML_DESCEND); + assert_non_null(cwmp_fault); + n = mxmlFindElement(cwmp_fault, cwmp_fault, "FaultCode", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + assert_string_equal(n->child->value.opaque, "9005"); + n = mxmlFindElement(cwmp_fault, cwmp_fault, "FaultString", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + MXML_DELETE(session->tree_in); + MXML_DELETE(session->tree_out); + + /* + * Not writable & Valid object path + */ + cwmp_fault = NULL; + prepare_addobj_soap_request(session, "Device.DeviceInfo.Processor."); + prepare_session_for_rpc_method_call(session); + + ret = cwmp_handle_rpc_cpe_add_object(session, rpc_cpe); + assert_int_equal(ret, 0); + + env = mxmlFindElement(session->tree_out, session->tree_out, "soap_env:Envelope", NULL, NULL, MXML_DESCEND); + assert_non_null(env); + n = mxmlFindElement(env, env, "soap_env:Header", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "cwmp:ID", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(env, env, "soap_env:Body", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(env, env, "soap_env:Fault", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "detail", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + cwmp_fault = mxmlFindElement(n, n, "cwmp:Fault", NULL, NULL, MXML_DESCEND); + assert_non_null(cwmp_fault); + n = mxmlFindElement(cwmp_fault, cwmp_fault, "FaultCode", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + assert_string_equal(n->child->value.opaque, "9005"); + n = mxmlFindElement(cwmp_fault, cwmp_fault, "FaultString", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + MXML_DELETE(session->tree_in); + MXML_DELETE(session->tree_out); + + session->head_rpc_acs.next = NULL; + unit_test_end_test_destruction(); + clean_name_space(); + session_test = NULL; +} + +static void prepare_delobj_soap_request(struct session *session, char *object) +{ + mxml_node_t *n = NULL; + + session->tree_in = mxmlLoadString(NULL, CWMP_DELOBJECT_REQ, MXML_OPAQUE_CALLBACK); + xml_recreate_namespace(session->tree_in); + n = mxmlFindElement(session->tree_in, session->tree_in, "cwmp:DeleteObject", NULL, NULL, MXML_DESCEND); + n = mxmlFindElement(n, n, "ObjectName", NULL, NULL, MXML_DESCEND); + n = mxmlNewOpaque(n, object); +} + +static void soap_delete_object_message_test(void **state) +{ + struct session *session = NULL; + mxml_node_t *env = NULL, *n = NULL, *add_resp = NULL; + struct rpc *rpc_cpe; + + create_session(&session); + session_test = session; + + rpc_cpe = list_entry(&(session->head_rpc_cpe), struct rpc, list); + + /* + * Valid path & writable object + */ + char del_obj[32]; + snprintf(del_obj, sizeof(del_obj), "Device.WiFi.SSID.%d.", instance); + prepare_delobj_soap_request(session, del_obj); + prepare_session_for_rpc_method_call(session); + + int ret = cwmp_handle_rpc_cpe_delete_object(session, rpc_cpe); + assert_int_equal(ret, 0); + env = mxmlFindElement(session->tree_out, session->tree_out, "soap_env:Envelope", NULL, NULL, MXML_DESCEND); + assert_non_null(env); + n = mxmlFindElement(env, env, "soap_env:Header", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "cwmp:ID", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(env, env, "soap_env:Body", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + add_resp = mxmlFindElement(n, n, "cwmp:DeleteObjectResponse", NULL, NULL, MXML_DESCEND); + assert_non_null(add_resp); + n = mxmlFindElement(add_resp, add_resp, "Status", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + assert_string_equal(n->child->value.opaque, "1"); + MXML_DELETE(session->tree_in); + MXML_DELETE(session->tree_out); + + /* + * Wrong object path + */ + mxml_node_t *cwmp_fault = NULL; + + prepare_delobj_soap_request(session, "Device.WiFi.SID.1"); + prepare_session_for_rpc_method_call(session); + + ret = cwmp_handle_rpc_cpe_delete_object(session, rpc_cpe); + assert_int_equal(ret, 0); + + env = mxmlFindElement(session->tree_out, session->tree_out, "soap_env:Envelope", NULL, NULL, MXML_DESCEND); + assert_non_null(env); + n = mxmlFindElement(env, env, "soap_env:Header", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "cwmp:ID", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(env, env, "soap_env:Body", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "soap_env:Fault", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "detail", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + cwmp_fault = mxmlFindElement(n, n, "cwmp:Fault", NULL, NULL, MXML_DESCEND); + assert_non_null(cwmp_fault); + n = mxmlFindElement(cwmp_fault, cwmp_fault, "FaultCode", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + assert_string_equal(n->child->value.opaque, "9005"); + n = mxmlFindElement(cwmp_fault, cwmp_fault, "FaultString", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + MXML_DELETE(session->tree_in); + MXML_DELETE(session->tree_out); + + /* + * Not writable & Valid object path + */ + cwmp_fault = NULL; + prepare_delobj_soap_request(session, "Device.DeviceInfo.Processor.2."); + prepare_session_for_rpc_method_call(session); + + ret = cwmp_handle_rpc_cpe_delete_object(session, rpc_cpe); + assert_int_equal(ret, 0); + + env = mxmlFindElement(session->tree_out, session->tree_out, "soap_env:Envelope", NULL, NULL, MXML_DESCEND); + assert_non_null(env); + n = mxmlFindElement(env, env, "soap_env:Header", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "cwmp:ID", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(env, env, "soap_env:Body", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(env, env, "soap_env:Fault", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "detail", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + cwmp_fault = mxmlFindElement(n, n, "cwmp:Fault", NULL, NULL, MXML_DESCEND); + assert_non_null(cwmp_fault); + n = mxmlFindElement(cwmp_fault, cwmp_fault, "FaultCode", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + assert_string_equal(n->child->value.opaque, "9005"); + n = mxmlFindElement(cwmp_fault, cwmp_fault, "FaultString", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + MXML_DELETE(session->tree_in); + MXML_DELETE(session->tree_out); + + session->head_rpc_acs.next = NULL; + unit_test_end_test_destruction(); + clean_name_space(); + session_test = NULL; +} + +static void prepare_gpa_soap_request(struct session *session, char *parameter) +{ + mxml_node_t *n = NULL; + + session->tree_in = mxmlLoadString(NULL, CWMP_GETATTRIBUTES_REQ, MXML_OPAQUE_CALLBACK); + xml_recreate_namespace(session->tree_in); + n = mxmlFindElement(session->tree_in, session->tree_in, "cwmp:GetParameterAttributes", NULL, NULL, MXML_DESCEND); + n = mxmlFindElement(n, n, "ParameterNames", NULL, NULL, MXML_DESCEND); + n = mxmlNewElement(n, "string"); + n = mxmlNewOpaque(n, parameter); +} + +static void soap_get_parameter_attributes_message_test(void **state) +{ + struct session *session = NULL; + mxml_node_t *env = NULL, *n = NULL, *param_attr = NULL; + struct rpc *rpc_cpe; + + create_session(&session); + session_test = session; + + rpc_cpe = list_entry(&(session->head_rpc_cpe), struct rpc, list); + + /* + * Valid path + */ + prepare_gpa_soap_request(session, "Device.DeviceInfo.UpTime"); + prepare_session_for_rpc_method_call(session); + + int ret = cwmp_handle_rpc_cpe_get_parameter_attributes(session, rpc_cpe); + assert_int_equal(ret, 0); + + env = mxmlFindElement(session->tree_out, session->tree_out, "soap_env:Envelope", NULL, NULL, MXML_DESCEND); + assert_non_null(env); + n = mxmlFindElement(env, env, "soap_env:Header", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "cwmp:ID", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(env, env, "soap_env:Body", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "cwmp:GetParameterAttributesResponse", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "ParameterList", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + param_attr = mxmlFindElement(n, n, "ParameterAttributeStruct", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(param_attr, param_attr, "Name", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + assert_string_equal(n->child->value.opaque, "Device.DeviceInfo.UpTime"); + n = mxmlFindElement(param_attr, param_attr, "Notification", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(param_attr, param_attr, "AccessList", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + + MXML_DELETE(session->tree_in); + MXML_DELETE(session->tree_out); + + /* + * Not Valid path + */ + mxml_node_t *fault_code = NULL, *fault_string = NULL, *detail = NULL, *detail_code = NULL, *detail_string = NULL; + + char *invalid_parameter[1] = { "Device.DeviceInfo.pTime" }; + prepare_gpv_soap_request(session, invalid_parameter, 1); + + prepare_session_for_rpc_method_call(session); + + ret = cwmp_handle_rpc_cpe_get_parameter_values(session, rpc_cpe); + assert_int_equal(ret, 0); + + env = mxmlFindElement(session->tree_out, session->tree_out, "soap_env:Envelope", NULL, NULL, MXML_DESCEND); + assert_non_null(env); + n = mxmlFindElement(env, env, "soap_env:Header", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "cwmp:ID", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(env, env, "soap_env:Body", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "soap_env:Fault", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + fault_code = mxmlFindElement(n, n, "faultcode", NULL, NULL, MXML_DESCEND); + assert_non_null(fault_code); + fault_string = mxmlFindElement(n, n, "faultstring", NULL, NULL, MXML_DESCEND); + assert_non_null(fault_string); + detail = mxmlFindElement(n, n, "detail", NULL, NULL, MXML_DESCEND); + assert_non_null(detail); + detail = mxmlFindElement(detail, detail, "cwmp:Fault", NULL, NULL, MXML_DESCEND); + assert_non_null(detail); + detail_code = mxmlFindElement(detail, detail, "FaultCode", NULL, NULL, MXML_DESCEND); + assert_non_null(detail_code); + assert_string_equal(detail_code->child->value.opaque, "9005"); + detail_string = mxmlFindElement(detail, detail, "FaultString", NULL, NULL, MXML_DESCEND); + assert_non_null(detail_string); + MXML_DELETE(session->tree_in); + MXML_DELETE(session->tree_out); + + session->head_rpc_acs.next = NULL; + unit_test_end_test_destruction(); + clean_name_space(); + session_test = NULL; +} + +static void prepare_spa_soap_request(struct session *session, char *parameter, char *notification, char *notification_change) +{ + mxml_node_t *n = NULL, *set_attr = NULL; + + session->tree_in = mxmlLoadString(NULL, CWMP_SETATTRIBUTES_REQ, MXML_OPAQUE_CALLBACK); + xml_recreate_namespace(session->tree_in); + set_attr = mxmlFindElement(session->tree_in, session->tree_in, "SetParameterAttributesStruct", NULL, NULL, MXML_DESCEND); + n = mxmlFindElement(set_attr, set_attr, "Name", NULL, NULL, MXML_DESCEND); + n = mxmlNewOpaque(n, parameter); + n = mxmlFindElement(set_attr, set_attr, "Notification", NULL, NULL, MXML_DESCEND); + n = mxmlNewOpaque(n, notification); + n = mxmlFindElement(set_attr, set_attr, "NotificationChange", NULL, NULL, MXML_DESCEND); + n = mxmlNewOpaque(n, notification_change); +} + +static void soap_set_parameter_attributes_message_test(void **state) +{ + struct session *session = NULL; + mxml_node_t *env = NULL, *n = NULL; + struct rpc *rpc_cpe; + + create_session(&session); + session_test = session; + + rpc_cpe = list_entry(&(session->head_rpc_cpe), struct rpc, list); + + /* + * Valid path + */ + prepare_spa_soap_request(session, "Device.DeviceInfo.UpTime", "1", "true"); + prepare_session_for_rpc_method_call(session); + + int ret = cwmp_handle_rpc_cpe_set_parameter_attributes(session, rpc_cpe); + assert_int_equal(ret, 0); + + env = mxmlFindElement(session->tree_out, session->tree_out, "soap_env:Envelope", NULL, NULL, MXML_DESCEND); + assert_non_null(env); + n = mxmlFindElement(env, env, "soap_env:Header", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "cwmp:ID", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(env, env, "soap_env:Body", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "cwmp:SetParameterAttributesResponse", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + assert_null(n->child); + MXML_DELETE(session->tree_in); + MXML_DELETE(session->tree_out); + + /* + * Not Valid path + */ + mxml_node_t *cwmp_fault = NULL; + prepare_spa_soap_request(session, "Device.DeviceInfo.pTime", "1", "true"); + prepare_session_for_rpc_method_call(session); + + ret = cwmp_handle_rpc_cpe_set_parameter_attributes(session, rpc_cpe); + assert_int_equal(ret, 0); + + env = mxmlFindElement(session->tree_out, session->tree_out, "soap_env:Envelope", NULL, NULL, MXML_DESCEND); + assert_non_null(env); + n = mxmlFindElement(env, env, "soap_env:Header", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "cwmp:ID", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(env, env, "soap_env:Body", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "soap_env:Fault", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "detail", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + cwmp_fault = mxmlFindElement(n, n, "cwmp:Fault", NULL, NULL, MXML_DESCEND); + assert_non_null(cwmp_fault); + n = mxmlFindElement(cwmp_fault, cwmp_fault, "FaultCode", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + assert_string_equal(n->child->value.opaque, "9005"); + n = mxmlFindElement(cwmp_fault, cwmp_fault, "FaultString", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + + MXML_DELETE(session->tree_in); + MXML_DELETE(session->tree_out); + + /* + * Not Valid Notification + */ + prepare_spa_soap_request(session, "Device.DeviceInfo.UpTime", "8", "true"); + prepare_session_for_rpc_method_call(session); + + ret = cwmp_handle_rpc_cpe_set_parameter_attributes(session, rpc_cpe); + assert_int_equal(ret, 0); + + env = mxmlFindElement(session->tree_out, session->tree_out, "soap_env:Envelope", NULL, NULL, MXML_DESCEND); + assert_non_null(env); + n = mxmlFindElement(env, env, "soap_env:Header", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "cwmp:ID", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(env, env, "soap_env:Body", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "soap_env:Fault", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "detail", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + cwmp_fault = mxmlFindElement(n, n, "cwmp:Fault", NULL, NULL, MXML_DESCEND); + assert_non_null(cwmp_fault); + n = mxmlFindElement(cwmp_fault, cwmp_fault, "FaultCode", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + assert_string_equal(n->child->value.opaque, "9003"); + n = mxmlFindElement(cwmp_fault, cwmp_fault, "FaultString", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + + MXML_DELETE(session->tree_in); + MXML_DELETE(session->tree_out); + + session->head_rpc_acs.next = NULL; + unit_test_end_test_destruction(); + clean_name_space(); + session_test = NULL; +} + +static void prepare_download_soap_request(struct session *session, char *url, char *file_type, char *username, char *password) +{ + mxml_node_t *n = NULL, *download = NULL; + session->tree_in = mxmlLoadString(NULL, CWMP_DOWNLOAD_REQ, MXML_OPAQUE_CALLBACK); + xml_recreate_namespace(session->tree_in); + download = mxmlFindElement(session->tree_in, session->tree_in, "cwmp:Download", NULL, NULL, MXML_DESCEND); + n = mxmlFindElement(download, download, "URL", NULL, NULL, MXML_DESCEND); + n = mxmlNewOpaque(n, url); + n = mxmlFindElement(download, download, "FileType", NULL, NULL, MXML_DESCEND); + n = mxmlNewOpaque(n, file_type); + n = mxmlFindElement(download, download, "Username", NULL, NULL, MXML_DESCEND); + n = mxmlNewOpaque(n, username); + n = mxmlFindElement(download, download, "Password", NULL, NULL, MXML_DESCEND); + n = mxmlNewOpaque(n, password); +} + +void free_download() +{ + struct download *download; + struct list_head *ilist, *q; + + if (list_download.next != &(list_download)) { + list_for_each_safe (ilist, q, &(list_download)) { + printf("%s:%s line %d\n", __FILE__, __FUNCTION__, __LINE__); + download = list_entry(ilist, struct download, list); + bkp_session_delete_download(download); + cwmp_free_download_request(download); + } + } +} + +static void soap_download_message_test(void **state) //TODO will be properly done with Download unit tests +{ + struct session *session = NULL; + mxml_node_t *env = NULL, *n = NULL, *download_node = NULL; + struct rpc *rpc_cpe; + + create_session(&session); + session_test = session; + + rpc_cpe = list_entry(&(session->head_rpc_cpe), struct rpc, list); + + /* + * Valid Arguments + */ + prepare_download_soap_request(session, "http://192.168.1.160/tr069/DG400PRIME-A-IOPSYS-6.2.0BETA1-210530_2348_nand_squashfs_update.pkgtb", "6 Stored Firmware Image", "iopsys", "iopsys"); + prepare_session_for_rpc_method_call(session); + int ret = cwmp_handle_rpc_cpe_download(session, rpc_cpe); + assert_int_equal(ret, 0); + + env = mxmlFindElement(session->tree_out, session->tree_out, "soap_env:Envelope", NULL, NULL, MXML_DESCEND); + assert_non_null(env); + n = mxmlFindElement(env, env, "soap_env:Header", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "cwmp:ID", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(env, env, "soap_env:Body", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + download_node = mxmlFindElement(n, n, "cwmp:DownloadResponse", NULL, NULL, MXML_DESCEND); + assert_non_null(download_node); + n = mxmlFindElement(download_node, download_node, "Status", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + assert_string_equal(n->child->value.opaque, "1"); + n = mxmlFindElement(download_node, download_node, "StartTime", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(download_node, download_node, "CompleteTime", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + + MXML_DELETE(session->tree_in); + MXML_DELETE(session->tree_out); + free_download(); + bkp_tree_clean(); + + /* + * wrong FileType + */ + + mxml_node_t *cwmp_fault = NULL; + prepare_download_soap_request(session, "http://192.168.1.160/tr069/DG400PRIME-A-IOPSYS-6.2.0BETA1-210530_2348_nand_squashfs_update.pkgtb", "7 System Certificate", "iopsys", "iopsys"); + prepare_session_for_rpc_method_call(session); + ret = cwmp_handle_rpc_cpe_download(session, rpc_cpe); + assert_int_equal(ret, 0); + + env = mxmlFindElement(session->tree_out, session->tree_out, "soap_env:Envelope", NULL, NULL, MXML_DESCEND); + assert_non_null(env); + n = mxmlFindElement(env, env, "soap_env:Header", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "cwmp:ID", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(env, env, "soap_env:Body", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + + + n = mxmlFindElement(n, n, "soap_env:Fault", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + n = mxmlFindElement(n, n, "detail", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + cwmp_fault = mxmlFindElement(n, n, "cwmp:Fault", NULL, NULL, MXML_DESCEND); + assert_non_null(cwmp_fault); + n = mxmlFindElement(cwmp_fault, cwmp_fault, "FaultCode", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + assert_string_equal(n->child->value.opaque, "9003"); + n = mxmlFindElement(cwmp_fault, cwmp_fault, "FaultString", NULL, NULL, MXML_DESCEND); + assert_non_null(n); + + MXML_DELETE(session->tree_in); + MXML_DELETE(session->tree_out); + free_download(); + bkp_tree_clean(); + + session->head_rpc_acs.next = NULL; + unit_test_end_test_destruction(); + clean_name_space(); + session_test = NULL; +} + +int main(void) +{ + const struct CMUnitTest tests[] = { // + cmocka_unit_test(get_config_test), cmocka_unit_test(get_deviceid_test), + cmocka_unit_test(add_event_test), + cmocka_unit_test(soap_inform_message_test), + cmocka_unit_test(soap_get_param_value_message_test), + //cmocka_unit_test(soap_set_param_value_message_test), + cmocka_unit_test(soap_add_object_message_test), + cmocka_unit_test(soap_delete_object_message_test), + cmocka_unit_test(soap_get_parameter_attributes_message_test), + cmocka_unit_test(soap_set_parameter_attributes_message_test), + //cmocka_unit_test(soap_download_message_test) //TODO will be properly done with Download unit tests + }; + + return cmocka_run_group_tests(tests, soap_unit_tests_init, soap_unit_tests_clean); +} diff --git a/test/cmocka/inc/icwmp_soap_msg_unit_test.h b/test/cmocka/inc/icwmp_soap_msg_unit_test.h new file mode 100644 index 0000000..f84fbe9 --- /dev/null +++ b/test/cmocka/inc/icwmp_soap_msg_unit_test.h @@ -0,0 +1,126 @@ +#ifndef __SOAP_MSG_TEST__ +#define __SOAP_MSG_TEST__ + +#define CWMP_GETPARAMETERVALUES_REQ \ + "" \ + "" \ + "ID:intrnl.unset.id.GetParameterValues1623750334191.21093494" \ + "0" \ + "" \ + "" \ + "" \ + "" \ + "" \ + "" \ + "" \ + "" + +#define CWMP_SETPARAMETERVALUES_REQ \ + "" \ + "" \ + "ID:intrnl.unset.id.SetParameterValues1624295944533.1489013116" \ + "0" \ + "" \ + "" \ + "" \ + "" \ + "" \ + "" \ + "" \ + "set_value_test" \ + "" \ + "" \ + "" + +#define CWMP_ADDOBJECT_REQ \ + "" \ + "" \ + "ID:intrnl.unset.id.AddObject1624461905714.1384387619" \ + "0" \ + "" \ + "" \ + "" \ + "" \ + "add_object_test" \ + "" \ + "" \ + "" + +#define CWMP_DELOBJECT_REQ \ + "" \ + "" \ + "ID:intrnl.unset.id.DeleteObject1624464905078.1243670982" \ + "0" \ + "" \ + "" \ + "" \ + "" \ + "del_object_test" \ + "" \ + "" \ + "" + +#define CWMP_GETATTRIBUTES_REQ \ + "" \ + "" \ + "ID:intrnl.unset.id.GetParameterAttributes1624541216937.139484077" \ + "0" \ + "" \ + "" \ + "" \ + "" \ + "" \ + "" \ + "" + +#define CWMP_SETATTRIBUTES_REQ \ + "" \ + "" \ + "ID:intrnl.unset.id.SetParameterAttributes1624546080334.1155903494" \ + "0" \ + "" \ + "" \ + "" \ + "" \ + "" \ + "" \ + "1" \ + "" \ + "subscriber" \ + "1" \ + "" \ + "" \ + "" \ + "" \ + "" + +#define CWMP_DOWNLOAD_REQ \ + "" \ + "" \ + "ID:intrnl.unset.id.Download1624556569149.1849926569" \ + "0" \ + "" \ + "" \ + "" \ + "download_test" \ + "" \ + "" \ + "" \ + "" \ + "0" \ + "" \ + "0" \ + "" \ + "" \ + "" \ + "" \ + "" + +#endif diff --git a/xml.c b/xml.c index 7db26c4..b8b358e 100755 --- a/xml.c +++ b/xml.c @@ -92,7 +92,7 @@ mxmlFindElementOpaque(mxml_node_t *node, /* I - Current node */ return (NULL); } -static int xml_recreate_namespace(mxml_node_t *tree) +int xml_recreate_namespace(mxml_node_t *tree) { const char *cwmp_urn; char *c; @@ -1162,7 +1162,6 @@ int cwmp_handle_rpc_cpe_get_parameter_values(struct session *session, struct rpc parameter_list = mxmlNewElement(n, "ParameterList"); if (!parameter_list) goto fault; - #ifdef ACS_MULTI mxmlElementSetAttr(parameter_list, "xsi:type", "soap_enc:Array"); #endif