pespin has uploaded this change for review.

View Change

WIP: Initial routing implementation based on extended-SLS

This commit adds a new set of APIs and structs to support routing based
on OPC,DPC,SLS fields and hence to support AS-loadshare.

The routing decision is still actually left as beforehand, ie. the first
AS/linkset in the combined_linkset is selected.

This will allow future work, i.e to:
- Check if data can be sent over the combined link (at least one
AS/linkset is ACTIVE), and otherwise try using a combined link with a
less specific match (shorter prefix mask or/and lower priority).
- Select one of the AS/linksets in the combined link based on a
round robin approach.

Related: SYS#7112
Change-Id: I0fb4ca4959096f748a23082efa0481300de56436
---
M include/osmocom/sigtran/osmo_ss7.h
M src/osmo_ss7_combined_linkset.c
M src/osmo_ss7_hmrt.c
M src/osmo_ss7_instance.c
M src/osmo_ss7_route.c
M src/osmo_ss7_route_table.c
M src/osmo_ss7_vty.c
M src/sccp_scrc.c
M src/ss7_combined_linkset.h
M src/ss7_instance.h
M src/ss7_route_table.h
M src/xua_rkm.c
M src/xua_snm.c
M tests/ss7/ss7_test.c
M tests/vty/osmo_stp_test.vty
15 files changed, 239 insertions(+), 42 deletions(-)

git pull ssh://gerrit.osmocom.org:29418/libosmo-sigtran refs/changes/77/39377/1
diff --git a/include/osmocom/sigtran/osmo_ss7.h b/include/osmocom/sigtran/osmo_ss7.h
index d35b870..eef0f25 100644
--- a/include/osmocom/sigtran/osmo_ss7.h
+++ b/include/osmocom/sigtran/osmo_ss7.h
@@ -125,7 +125,8 @@
struct osmo_ss7_route;

struct osmo_ss7_route *
-osmo_ss7_route_lookup(struct osmo_ss7_instance *inst, uint32_t dpc);
+osmo_ss7_route_lookup(struct osmo_ss7_instance *inst, uint32_t dpc)
+ OSMO_DEPRECATED("Use internal ss7_instance_lookup_route() instead");
const char *osmo_ss7_route_print(const struct osmo_ss7_route *rt);
const char *osmo_ss7_route_name(struct osmo_ss7_route *rt, bool list_asps);
struct osmo_ss7_as *
diff --git a/src/osmo_ss7_combined_linkset.c b/src/osmo_ss7_combined_linkset.c
index f7499b5..80a3813 100644
--- a/src/osmo_ss7_combined_linkset.c
+++ b/src/osmo_ss7_combined_linkset.c
@@ -111,9 +111,64 @@
void ss7_combined_link_del_route(struct osmo_ss7_route *rt)
{
struct osmo_ss7_combined_linkset *clset = rt->clset;
+
+ /* Remove route from eSLS table: */
+ for (unsigned int i = 0; i < ARRAY_SIZE(clset->esls_table); i++) {
+ if (clset->esls_table[i].cached_rt != rt)
+ continue;
+ clset->esls_table[i].cached_rt = NULL;
+ }
+
llist_del(&rt->list);
rt->clset = NULL;
clset->num_routes--;
if (clset->num_routes == 0)
ss7_combined_linkset_free(clset);
}
+
+static ext_sls_t osmo_ss7_instance_calc_itu_ext_sls(const struct osmo_ss7_instance *inst, const struct osmo_ss7_route_label *rtlabel)
+{
+ /* Take 6 bits from OPC and DPC according to config: */
+ uint8_t opc6 = (uint8_t)((rtlabel->opc >> inst->cfg.opc_shift) & 0x3f);
+ uint8_t dpc6 = (uint8_t)((rtlabel->dpc >> inst->cfg.dpc_shift) & 0x3f);
+
+ /* Derivate 3-bit value from OPC and DPC: */
+ uint8_t opc3 = ((opc6 >> 3) ^ (opc6 & 0x07)) & 0x07;
+ uint8_t dpc3 = ((dpc6 >> 3) ^ (dpc6 & 0x07)) & 0x07;
+ uint8_t opc_dpc3 = (opc3 ^ dpc3) & 0x07;
+
+ /* Generate 7 bit extended-SLS: 3-bit OPC-DPC + 4 bit SLS: */
+ uint8_t ext_sls = (opc_dpc3 << 4) | ((rtlabel->sls) & 0x0f);
+ OSMO_ASSERT(ext_sls < NUM_EXT_SLS);
+
+ /* Pick extended-SLS bits according to config: */
+ ext_sls = ext_sls >> inst->cfg.sls_shift;
+ return ext_sls;
+}
+
+struct osmo_ss7_route *
+ss7_combined_link_lookup_route(struct osmo_ss7_combined_linkset *clset, const struct osmo_ss7_route_label *rtlabel)
+{
+ struct osmo_ss7_route *rt;
+ ext_sls_t esls = osmo_ss7_instance_calc_itu_ext_sls(clset->rtable->inst, rtlabel);
+
+ /* First check if we have a cached route for this ESLS */
+ rt = clset->esls_table[esls].cached_rt;
+ if (rt) {
+ /* TODO: Check if the AS/linkset in rt is actually UP and can be
+ * used, otherwise we need to pick a temporary dst (update the
+ * esls_table entry) while the original one is DOWN. This is
+ * described iirc in ITU Q.704 or ITU Q.705 */
+ return rt;
+ }
+
+ /* We need to pick a new AS/linkset from the combined linkset and cache
+ * it so it is always used for this eSLS: */
+ /* FIXME: for now we simply take the first AS in the combined linksed, to be improved later... */
+ rt = llist_first_entry_or_null(&clset->routes, struct osmo_ss7_route, list);
+
+ /* TODO: here we'd need to actually check if dst AS/linkset in the route
+ * is actually UP, otherwise pick next one in the roundrobin list... */
+
+ return rt;
+}
diff --git a/src/osmo_ss7_hmrt.c b/src/osmo_ss7_hmrt.c
index c256860..38ff884 100644
--- a/src/osmo_ss7_hmrt.c
+++ b/src/osmo_ss7_hmrt.c
@@ -212,11 +212,16 @@
struct xua_msg *xua)
{
uint32_t dpc = xua->mtp.dpc;
+ struct osmo_ss7_route_label rtlabel = {
+ .opc = xua->mtp.opc,
+ .dpc = xua->mtp.dpc,
+ .sls = xua->mtp.sls,
+ };
struct osmo_ss7_route *rt;

- /* find route for DPC */
+ /* find route for OPC+DPC+SLS: */
/* FIXME: unify with gen_mtp_transfer_req_xua() */
- rt = osmo_ss7_route_lookup(inst, dpc);
+ rt = ss7_instance_lookup_route(inst, &rtlabel);
if (rt) {
/* FIXME: DPC SP restart? */
/* FIXME: DPC Congested? */
diff --git a/src/osmo_ss7_instance.c b/src/osmo_ss7_instance.c
index f7d9a41..527cf2a 100644
--- a/src/osmo_ss7_instance.c
+++ b/src/osmo_ss7_instance.c
@@ -202,6 +202,15 @@
return -1;
}

+/*! \brief Find a SS7 route for given destination point code in given SS7 */
+struct osmo_ss7_route *
+ss7_instance_lookup_route(struct osmo_ss7_instance *inst, const struct osmo_ss7_route_label *rtlabel)
+{
+ OSMO_ASSERT(ss7_initialized);
+ return ss7_route_table_lookup_route(inst->rtable_system, rtlabel);
+}
+
+
/***********************************************************************
* SS7 Application Server
***********************************************************************/
diff --git a/src/osmo_ss7_route.c b/src/osmo_ss7_route.c
index 20097ce..ce438f0 100644
--- a/src/osmo_ss7_route.c
+++ b/src/osmo_ss7_route.c
@@ -275,12 +275,21 @@
return buf;
}

-/*! \brief Find a SS7 route for given destination point code in given SS7 */
+/*! \brief Find a SS7 route for given destination point code in given SS7
+ *
+ * NOTE: DEPRECATED, use ss7_instance_lookup_route() instead
+ */
struct osmo_ss7_route *
osmo_ss7_route_lookup(struct osmo_ss7_instance *inst, uint32_t dpc)
{
OSMO_ASSERT(ss7_initialized);
- return ss7_route_table_find_route_by_dpc(inst->rtable_system, dpc);
+ struct osmo_ss7_route_label rtlb = {
+ .opc = 0,
+ .dpc = dpc,
+ .sls = 0,
+ };
+
+ return ss7_instance_lookup_route(inst, &rtlb);
}

/*! \brief Get destination AS of route
diff --git a/src/osmo_ss7_route_table.c b/src/osmo_ss7_route_table.c
index b230521..1a83fb6 100644
--- a/src/osmo_ss7_route_table.c
+++ b/src/osmo_ss7_route_table.c
@@ -83,25 +83,10 @@
talloc_free(rtbl);
}

-/*! \brief Find a SS7 route for given destination point code in given table */
-struct osmo_ss7_route *
-ss7_route_table_find_route_by_dpc(struct osmo_ss7_route_table *rtbl, uint32_t dpc)
-{
- struct osmo_ss7_combined_linkset *clset;
- struct osmo_ss7_route *rt;
-
- OSMO_ASSERT(ss7_initialized);
-
- dpc = osmo_ss7_pc_normalize(&rtbl->inst->cfg.pc_fmt, dpc);
-
- clset = ss7_route_table_find_combined_linkset_by_dpc(rtbl, dpc);
- if (!clset)
- return NULL;
- rt = llist_first_entry_or_null(&clset->routes, struct osmo_ss7_route, list);
- return rt;
-}
-
-/*! \brief Find a SS7 route for given destination point code + mask in given table */
+/*! \brief Find a SS7 route for given destination point code + mask in given table.
+ *
+ * This function is used for route management procedures, not for packet routing lookup procedures!
+ */
struct osmo_ss7_route *
ss7_route_table_find_route_by_dpc_mask(struct osmo_ss7_route_table *rtbl, uint32_t dpc,
uint32_t mask)
@@ -227,3 +212,27 @@
}
}
}
+
+struct osmo_ss7_route *
+ss7_route_table_lookup_route(struct osmo_ss7_route_table *rtbl, const struct osmo_ss7_route_label *rtlabel)
+{
+ struct osmo_ss7_combined_linkset *clset;
+ struct osmo_ss7_route *rt;
+ struct osmo_ss7_route_label rtlb = {
+ .opc = osmo_ss7_pc_normalize(&rtbl->inst->cfg.pc_fmt, rtlabel->opc),
+ .dpc = osmo_ss7_pc_normalize(&rtbl->inst->cfg.pc_fmt, rtlabel->dpc),
+ .sls = rtlabel->sls,
+ };
+ /* we assume the combined_links are sorted by mask length, i.e. more
+ * specific combined links first, and less specific combined links with shorter
+ * mask later */
+ llist_for_each_entry(clset, &rtbl->combined_linksets, list) {
+ if ((rtlb.dpc & clset->cfg.mask) != clset->cfg.pc)
+ continue;
+ rt = ss7_combined_link_lookup_route(clset, &rtlb);
+ if (!rt)
+ continue;
+ return rt;
+ }
+ return NULL;
+}
diff --git a/src/osmo_ss7_vty.c b/src/osmo_ss7_vty.c
index 547b420..cb85f39 100644
--- a/src/osmo_ss7_vty.c
+++ b/src/osmo_ss7_vty.c
@@ -290,6 +290,41 @@
return CMD_SUCCESS;
}

+
+DEFUN_ATTR(cs7_opc_dpc_shift, cs7_opc_dpc_shift_cmd,
+ "sls-opc-dpc [opc-shift] [<0-8>] [dpc-shift] [<0-8>]",
+ "Shift OPC and DPC bits used during routing decision\n"
+ "Shift OPC bits used during routing decision\n"
+ "How many bits from ITU OPC field (starting from least-significant-bit) to skip (default=0). 6 bits are always used\n"
+ "Shift DPC bits used during routing decision\n"
+ "How many bits from ITU DPC field (starting from least-significant-bit) to skip (default=0). 6 bits are always used\n",
+ CMD_ATTR_IMMEDIATE)
+{
+ struct osmo_ss7_instance *inst = vty->index;
+ if (argc == 4)
+ inst->cfg.dpc_shift = atoi(argv[3]);
+ else if (argc == 3)
+ inst->cfg.dpc_shift = 0;
+ if (argc >= 2)
+ inst->cfg.opc_shift = atoi(argv[1]);
+ else if (argc == 1)
+ inst->cfg.opc_shift = 0;
+
+ return CMD_SUCCESS;
+}
+
+DEFUN_ATTR(cs7_sls_shift, cs7_sls_shift_cmd,
+ "sls-shift <0-6>",
+ "Shift SLS bits used during routing decision\n"
+ "How many bits from derivated 7-bit extended-SLS (OPC, DPC, SLS) field (starting from least-significant-bit) to skip\n",
+ CMD_ATTR_IMMEDIATE)
+{
+ struct osmo_ss7_instance *inst = vty->index;
+ inst->cfg.sls_shift = atoi(argv[0]);
+
+ return CMD_SUCCESS;
+}
+
static void write_one_cs7(struct vty *vty, struct osmo_ss7_instance *inst, bool show_dyn_config);

static int write_all_cs7(struct vty *vty, bool show_dyn_config)
@@ -2900,6 +2935,13 @@
if (inst->cfg.permit_dyn_rkm_alloc)
vty_out(vty, " xua rkm routing-key-allocation dynamic-permitted%s", VTY_NEWLINE);

+ if (inst->cfg.opc_shift != 0 || inst->cfg.dpc_shift != 0)
+ vty_out(vty, " sls-opc-dpc opc-shift %u dpc-shift %u%s",
+ inst->cfg.opc_shift, inst->cfg.dpc_shift, VTY_NEWLINE);
+
+ if (inst->cfg.sls_shift != 0)
+ vty_out(vty, " sls-shift %u%s", inst->cfg.sls_shift, VTY_NEWLINE);
+
/* first dump ASPs, as ASs reference them */
llist_for_each_entry(asp, &inst->asp_list, list)
write_one_asp(vty, asp, show_dyn_config);
@@ -3062,6 +3104,8 @@
install_lib_element(L_CS7_NODE, &cs7_pc_format_def_cmd);
install_lib_element(L_CS7_NODE, &cs7_pc_delimiter_cmd);
install_lib_element(L_CS7_NODE, &cs7_permit_dyn_rkm_cmd);
+ install_lib_element(L_CS7_NODE, &cs7_opc_dpc_shift_cmd);
+ install_lib_element(L_CS7_NODE, &cs7_sls_shift_cmd);

install_node(&asp_node, NULL);
install_lib_element_ve(&show_cs7_asp_cmd);
diff --git a/src/sccp_scrc.c b/src/sccp_scrc.c
index 23c3f2d..869235c 100644
--- a/src/sccp_scrc.c
+++ b/src/sccp_scrc.c
@@ -37,6 +37,7 @@
#include "ss7_instance.h"
#include "ss7_linkset.h"
#include "ss7_route.h"
+#include "ss7_route_table.h"
#include "xua_internal.h"


@@ -120,6 +121,7 @@
const struct osmo_sccp_addr *called)
{
struct osmo_ss7_route *rt;
+ struct osmo_ss7_route_label rtlabel;

/* this is a bit fishy due to the different requirements of
* classic SSCP/MTP compared to various SIGTRAN stackings.
@@ -144,7 +146,13 @@
return -1;
}

- rt = osmo_ss7_route_lookup(inst->ss7, xua->mtp.dpc);
+ rtlabel = (struct osmo_ss7_route_label){
+ .opc = xua->mtp.opc,
+ .dpc = xua->mtp.dpc,
+ .sls = xua->mtp.sls,
+ };
+
+ rt = ss7_instance_lookup_route(inst->ss7, &rtlabel);
if (!rt) {
LOGP(DLSCCP, LOGL_ERROR, "MTP-TRANSFER.req from SCCP for "
"DPC %u: no route!\n", xua->mtp.dpc);
diff --git a/src/ss7_combined_linkset.h b/src/ss7_combined_linkset.h
index c353f03..76131a1 100644
--- a/src/ss7_combined_linkset.h
+++ b/src/ss7_combined_linkset.h
@@ -10,6 +10,14 @@

struct osmo_ss7_instance;
struct osmo_ss7_link;
+struct osmo_ss7_route_label;
+
+#define NUM_EXT_SLS 128
+typedef uint8_t ext_sls_t; /* range: 0-127, 7 bit */
+
+struct osmo_ss7_esls_entry {
+ struct osmo_ss7_route *cached_rt;
+};

struct osmo_ss7_combined_linkset {
/*! member in \ref osmo_ss7_route_table.combined_linksets */
@@ -17,6 +25,7 @@

/*! \ref osmo_ss7_route_table to which we belong */
struct osmo_ss7_route_table *rtable;
+ struct osmo_ss7_esls_entry esls_table[NUM_EXT_SLS];

/*! list of \ref osmo_ss7_route */
struct llist_head routes;
@@ -41,3 +50,5 @@
ss7_combined_link_add_route(struct osmo_ss7_combined_linkset *clset, struct osmo_ss7_route *rt);
void
ss7_combined_link_del_route(struct osmo_ss7_route *rt);
+struct osmo_ss7_route *
+ss7_combined_link_lookup_route(struct osmo_ss7_combined_linkset *clset, const struct osmo_ss7_route_label *rtlabel);
diff --git a/src/ss7_instance.h b/src/ss7_instance.h
index d76891f..bb8815b 100644
--- a/src/ss7_instance.h
+++ b/src/ss7_instance.h
@@ -10,6 +10,7 @@

struct osmo_ss7_user;
struct osmo_ss7_route_table;
+struct osmo_ss7_route_label;
struct osmo_sccp_instance;

struct osmo_ss7_pc_fmt {
@@ -49,6 +50,15 @@
bool permit_dyn_rkm_alloc;
struct llist_head sccp_address_book;
uint32_t secondary_pc;
+ /* How many bits from ITU OPC/DPC field (starting from least-significant-bit)
+ * to skip for routing decisions (always takes 6 bits).
+ * range 0-8, defaults to 0, which means take least significant 6 bits. */
+ uint8_t opc_shift;
+ uint8_t dpc_shift;
+ /* How many bits from ITU SLS field (starting from least-significant-bit)
+ * to skip for routing decisions.
+ * range 0-3, defaults to 0, which means take all 4 bits. */
+ uint8_t sls_shift;
} cfg;
};

@@ -56,6 +66,8 @@
ss7_instance_alloc(void *ctx, uint32_t id);

uint32_t ss7_find_free_l_rk_id(struct osmo_ss7_instance *inst);
+struct osmo_ss7_route *
+ss7_instance_lookup_route(struct osmo_ss7_instance *inst, const struct osmo_ss7_route_label *rtlabel);

#define _LOGSS7(inst, subsys, level, fmt, args ...) \
LOGP(subsys, level, "%u: " fmt, inst ? (inst)->cfg.id : 0, ## args)
diff --git a/src/ss7_route_table.h b/src/ss7_route_table.h
index c88c742..e63933c 100644
--- a/src/ss7_route_table.h
+++ b/src/ss7_route_table.h
@@ -9,6 +9,12 @@

struct osmo_ss7_instance;

+struct osmo_ss7_route_label {
+ uint32_t opc;
+ uint32_t dpc;
+ uint8_t sls;
+};
+
struct osmo_ss7_route_table {
/*! member in list of routing tables */
struct llist_head list;
@@ -30,10 +36,10 @@
void ss7_route_table_destroy(struct osmo_ss7_route_table *rtbl);

struct osmo_ss7_route *
-ss7_route_table_find_route_by_dpc(struct osmo_ss7_route_table *rtbl, uint32_t dpc);
-struct osmo_ss7_route *
ss7_route_table_find_route_by_dpc_mask(struct osmo_ss7_route_table *rtbl, uint32_t dpc,
uint32_t mask);
+struct osmo_ss7_route *
+ss7_route_table_lookup_route(struct osmo_ss7_route_table *rtbl, const struct osmo_ss7_route_label *rtlabel);

struct osmo_ss7_combined_linkset *
ss7_route_table_find_combined_linkset(struct osmo_ss7_route_table *rtbl, uint32_t dpc, uint32_t mask, uint32_t prio);
diff --git a/src/xua_rkm.c b/src/xua_rkm.c
index 9a3918e..97aeca5 100644
--- a/src/xua_rkm.c
+++ b/src/xua_rkm.c
@@ -377,7 +377,7 @@
return -1;
}

- rt = ss7_route_table_find_route_by_dpc(inst->rtable_system, as->cfg.routing_key.pc);
+ rt = ss7_route_table_find_route_by_dpc_mask(inst->rtable_system, as->cfg.routing_key.pc, 0xffffff);
if (!rt) {
msgb_append_dereg_res(resp, M3UA_RKM_DEREG_ERR_UNKNOWN, 0);
return -1;
diff --git a/src/xua_snm.c b/src/xua_snm.c
index 36fe3c7..6edbbe8 100644
--- a/src/xua_snm.c
+++ b/src/xua_snm.c
@@ -34,6 +34,7 @@
#include "ss7_as.h"
#include "ss7_asp.h"
#include "ss7_internal.h"
+#include "ss7_route_table.h"
#include "xua_internal.h"
#include "sccp_internal.h"

@@ -340,8 +341,14 @@
if (mask == 0) {
/* one single point code */

+ struct osmo_ss7_route_label rtlabel = {
+ .opc = xua->mtp.dpc, /* FIXME: Correct? use DPC of received DAUD as OPC. */
+ .dpc = pc,
+ .sls = 0,
+ };
+
/* FIXME: don't just check for a route; but also check if the route is "active" */
- if (osmo_ss7_route_lookup(s7i, pc))
+ if (ss7_instance_lookup_route(s7i, &rtlabel))
is_available = true;

xua_tx_snm_available(asp, rctx, num_rctx, &aff_pc[i], 1, "Response to DAUD",
diff --git a/tests/ss7/ss7_test.c b/tests/ss7/ss7_test.c
index 6fe1110..95fa1b1 100644
--- a/tests/ss7/ss7_test.c
+++ b/tests/ss7/ss7_test.c
@@ -147,11 +147,15 @@
osmo_ss7_user_destroy(user2);
}

+#define RT_LABEL(opc_val, dpc_val, sls_val) \
+ (struct osmo_ss7_route_label){ .opc = (opc_val), .dpc = (dpc_val), .sls = (sls_val) }
+
static void test_route(void)
{
struct osmo_ss7_route_table *rtbl;
struct osmo_ss7_linkset *lset_a, *lset_b;
struct osmo_ss7_route *rt, *rt12, *rtdef;
+ struct osmo_ss7_route_label route_label;

printf("Testing SS7 routing\n");

@@ -173,32 +177,45 @@
OSMO_ASSERT(lset_b);

/* route with full mask */
- OSMO_ASSERT(ss7_route_table_find_route_by_dpc(rtbl, 12) == NULL);
+ route_label = RT_LABEL(0, 12, 0);
+ OSMO_ASSERT(ss7_route_table_lookup_route(rtbl, &route_label) == NULL);
rt = ss7_route_create(rtbl, 12, 0xffff, "a");
printf("route with full mask: %s\n", osmo_ss7_route_print(rt));
OSMO_ASSERT(rt);
- OSMO_ASSERT(ss7_route_table_find_route_by_dpc(rtbl, 12) == rt);
+ route_label = RT_LABEL(0, 12, 0);
+ OSMO_ASSERT(ss7_route_table_lookup_route(rtbl, &route_label) == rt);
ss7_route_destroy(rt);

/* route with partial mask */
rt = ss7_route_create(rtbl, 8, 0xfff8, "a");
printf("route with partial mask: %s\n", osmo_ss7_route_print(rt));
- OSMO_ASSERT(ss7_route_table_find_route_by_dpc(rtbl, 8) == rt);
- OSMO_ASSERT(ss7_route_table_find_route_by_dpc(rtbl, 9) == rt);
- OSMO_ASSERT(ss7_route_table_find_route_by_dpc(rtbl, 12) == rt);
- OSMO_ASSERT(ss7_route_table_find_route_by_dpc(rtbl, 15) == rt);
- OSMO_ASSERT(ss7_route_table_find_route_by_dpc(rtbl, 16) == NULL);
+ route_label = RT_LABEL(0, 8, 0);
+ OSMO_ASSERT(ss7_route_table_lookup_route(rtbl, &route_label) == rt);
+ route_label = RT_LABEL(0, 9, 0);
+ OSMO_ASSERT(ss7_route_table_lookup_route(rtbl, &route_label) == rt);
+ route_label = RT_LABEL(0, 12, 0);
+ OSMO_ASSERT(ss7_route_table_lookup_route(rtbl, &route_label) == rt);
+ route_label = RT_LABEL(0, 15, 0);
+ OSMO_ASSERT(ss7_route_table_lookup_route(rtbl, &route_label) == rt);
+ route_label = RT_LABEL(0, 16, 0);
+ OSMO_ASSERT(ss7_route_table_lookup_route(rtbl, &route_label) == NULL);
/* insert more specific route for 12, must have higher priority
* than existing one */
rt12 = ss7_route_create(rtbl, 12, 0xffff, "b");
- OSMO_ASSERT(ss7_route_table_find_route_by_dpc(rtbl, 12) == rt12);
- OSMO_ASSERT(ss7_route_table_find_route_by_dpc(rtbl, 15) == rt);
- OSMO_ASSERT(ss7_route_table_find_route_by_dpc(rtbl, 16) == NULL);
+ route_label = RT_LABEL(0, 12, 0);
+ OSMO_ASSERT(ss7_route_table_lookup_route(rtbl, &route_label) == rt12);
+ route_label = RT_LABEL(0, 15, 0);
+ OSMO_ASSERT(ss7_route_table_lookup_route(rtbl, &route_label) == rt);
+ route_label = RT_LABEL(0, 16, 0);
+ OSMO_ASSERT(ss7_route_table_lookup_route(rtbl, &route_label) == NULL);
/* add a default route, which should have lowest precedence */
rtdef = ss7_route_create(rtbl, 0, 0, "a");
- OSMO_ASSERT(ss7_route_table_find_route_by_dpc(rtbl, 12) == rt12);
- OSMO_ASSERT(ss7_route_table_find_route_by_dpc(rtbl, 15) == rt);
- OSMO_ASSERT(ss7_route_table_find_route_by_dpc(rtbl, 16) == rtdef);
+ route_label = RT_LABEL(0, 12, 0);
+ OSMO_ASSERT(ss7_route_table_lookup_route(rtbl, &route_label) == rt12);
+ route_label = RT_LABEL(0, 15, 0);
+ OSMO_ASSERT(ss7_route_table_lookup_route(rtbl, &route_label) == rt);
+ route_label = RT_LABEL(0, 16, 0);
+ OSMO_ASSERT(ss7_route_table_lookup_route(rtbl, &route_label) == rtdef);

ss7_route_destroy(rtdef);
ss7_route_destroy(rt12);
diff --git a/tests/vty/osmo_stp_test.vty b/tests/vty/osmo_stp_test.vty
index cb24560..aa9ed77 100644
--- a/tests/vty/osmo_stp_test.vty
+++ b/tests/vty/osmo_stp_test.vty
@@ -109,6 +109,8 @@
point-code format default
point-code delimiter (default|dash)
xua rkm routing-key-allocation (static-only|dynamic-permitted)
+ sls-opc-dpc [opc-shift] [<0-8>] [dpc-shift] [<0-8>]
+ sls-shift <0-6>
asp NAME <0-65535> <0-65535> (sua|m3ua|ipa)
asp NAME <0-65535> <0-65535> (sua|m3ua|ipa) (sctp|tcp)
no asp NAME
@@ -129,6 +131,8 @@
point-code Configure the local Point Code
secondary-pc Configure the local Secondary Point Code
xua SIGTRAN xxxUA related
+ sls-opc-dpc Shift OPC and DPC bits used during routing decision
+ sls-shift Shift SLS bits used during routing decision
asp Configure Application Server Process
no Negate a command or set its defaults
as Configure an Application Server

To view, visit change 39377. To unsubscribe, or for help writing mail filters, visit settings.

Gerrit-MessageType: newchange
Gerrit-Project: libosmo-sigtran
Gerrit-Branch: master
Gerrit-Change-Id: I0fb4ca4959096f748a23082efa0481300de56436
Gerrit-Change-Number: 39377
Gerrit-PatchSet: 1
Gerrit-Owner: pespin <pespin@sysmocom.de>