summaryrefslogtreecommitdiffstats
path: root/openbsc/src
diff options
context:
space:
mode:
authorHolger Hans Peter Freyther <holger@moiji-mobile.com>2016-04-06 22:41:12 +0200
committerHolger Hans Peter Freyther <holger@moiji-mobile.com>2016-04-07 09:27:07 +0200
commit9bcb1a56cbec710cbfa49ae6623c10595eab08ec (patch)
treec294e740388080d889402fef9475aa8c9cb6f0af /openbsc/src
parentadb86759daa80a484eef4b5a24bc0ce0de0a0763 (diff)
ctrl: Extend ctrl command to optionally handle alg+ki
Extend the existing ctrl command to be able to specify the algorithm and Ki. In contrast to the VTY no size check is done. Together with the VTY this code only supports a small part of what is supported by libosmocore. The algorithm and ki are considered optional but if a valid algorithm other than "none" is passed, a KI must be passed as well. Extend the test coverage by passing the potential values. It is not verified that the KI/algorithm is stored.
Diffstat (limited to 'openbsc/src')
-rw-r--r--openbsc/src/libmsc/ctrl_commands.c60
1 files changed, 58 insertions, 2 deletions
diff --git a/openbsc/src/libmsc/ctrl_commands.c b/openbsc/src/libmsc/ctrl_commands.c
index e48c6a3..9ac39de 100644
--- a/openbsc/src/libmsc/ctrl_commands.c
+++ b/openbsc/src/libmsc/ctrl_commands.c
@@ -24,9 +24,25 @@
#include <openbsc/db.h>
#include <openbsc/debug.h>
+static bool alg_supported(const char *alg)
+{
+ /*
+ * TODO: share this with the vty_interface and extend to all
+ * algorithms supported by libosmocore now. Make it table based
+ * as well.
+ */
+ if (strcasecmp(alg, "none") == 0)
+ return true;
+ if (strcasecmp(alg, "xor") == 0)
+ return true;
+ if (strcasecmp(alg, "comp128v1") == 0)
+ return true;
+ return false;
+}
+
static int verify_subscriber_modify(struct ctrl_cmd *cmd, const char *value, void *d)
{
- char *tmp, *imsi, *msisdn, *saveptr = NULL;
+ char *tmp, *imsi, *msisdn, *alg, *ki, *saveptr = NULL;
int rc = 0;
tmp = talloc_strdup(cmd, value);
@@ -35,6 +51,8 @@ static int verify_subscriber_modify(struct ctrl_cmd *cmd, const char *value, voi
imsi = strtok_r(tmp, ",", &saveptr);
msisdn = strtok_r(NULL, ",", &saveptr);
+ alg = strtok_r(NULL, ",", &saveptr);
+ ki = strtok_r(NULL, ",", &saveptr);
if (!imsi || !msisdn)
rc = 1;
@@ -42,6 +60,12 @@ static int verify_subscriber_modify(struct ctrl_cmd *cmd, const char *value, voi
rc = 1;
else if (strlen(msisdn) >= GSM_EXTENSION_LENGTH)
rc = 1;
+ else if (alg) {
+ if (!alg_supported(alg))
+ rc = 1;
+ else if (strcasecmp(alg, "none") != 0 && !ki)
+ rc = 1;
+ }
talloc_free(tmp);
return rc;
@@ -56,7 +80,7 @@ static int get_subscriber_modify(struct ctrl_cmd *cmd, void *data)
static int set_subscriber_modify(struct ctrl_cmd *cmd, void *data)
{
struct gsm_network *net = cmd->node;
- char *tmp, *imsi, *msisdn, *saveptr = NULL;
+ char *tmp, *imsi, *msisdn, *alg, *ki, *saveptr = NULL;
struct gsm_subscriber* subscr;
int rc;
@@ -66,6 +90,8 @@ static int set_subscriber_modify(struct ctrl_cmd *cmd, void *data)
imsi = strtok_r(tmp, ",", &saveptr);
msisdn = strtok_r(NULL, ",", &saveptr);
+ alg = strtok_r(NULL, ",", &saveptr);
+ ki = strtok_r(NULL, ",", &saveptr);
subscr = subscr_get_by_imsi(net->subscr_group, imsi);
if (!subscr)
@@ -80,6 +106,36 @@ static int set_subscriber_modify(struct ctrl_cmd *cmd, void *data)
/* put it back to the db */
rc = db_sync_subscriber(subscr);
db_subscriber_update(subscr);
+
+ /* handle optional ciphering */
+ if (alg) {
+ if (strcasecmp(alg, "none") == 0)
+ db_sync_authinfo_for_subscr(NULL, subscr);
+ else {
+ struct gsm_auth_info ainfo = { 0, };
+ /* the verify should make sure that this is okay */
+ OSMO_ASSERT(alg);
+ OSMO_ASSERT(ki);
+
+ if (strcasecmp(alg, "xor") == 0)
+ ainfo.auth_algo = AUTH_ALGO_XOR;
+ else if (strcasecmp(alg, "comp128v1") == 0)
+ ainfo.auth_algo = AUTH_ALGO_COMP128v1;
+
+ rc = osmo_hexparse(ki, ainfo.a3a8_ki, sizeof(ainfo.a3a8_ki));
+ if (rc < 0) {
+ subscr_put(subscr);
+ talloc_free(tmp);
+ cmd->reply = "Failed to parse KI";
+ return CTRL_CMD_ERROR;
+ }
+
+ ainfo.a3a8_ki_len = rc;
+ db_sync_authinfo_for_subscr(&ainfo, subscr);
+ rc = 0;
+ }
+ db_sync_lastauthtuple_for_subscr(NULL, subscr);
+ }
subscr_put(subscr);
talloc_free(tmp);