diff options
Diffstat (limited to 'openbsc/include')
-rw-r--r-- | openbsc/include/openbsc/Makefile.am | 6 | ||||
-rw-r--r-- | openbsc/include/openbsc/bsc_api.h | 2 | ||||
-rw-r--r-- | openbsc/include/openbsc/bss.h | 5 | ||||
-rw-r--r-- | openbsc/include/openbsc/debug.h | 3 | ||||
-rw-r--r-- | openbsc/include/openbsc/gprs_gmm.h | 4 | ||||
-rw-r--r-- | openbsc/include/openbsc/gprs_sgsn.h | 88 | ||||
-rw-r--r-- | openbsc/include/openbsc/gsm_04_08.h | 2 | ||||
-rw-r--r-- | openbsc/include/openbsc/gsm_04_08_gprs.h | 21 | ||||
-rw-r--r-- | openbsc/include/openbsc/gsm_04_11.h | 2 | ||||
-rw-r--r-- | openbsc/include/openbsc/gsm_04_80.h | 3 | ||||
-rw-r--r-- | openbsc/include/openbsc/gsm_data.h | 90 | ||||
-rw-r--r-- | openbsc/include/openbsc/gsm_data_shared.h | 19 | ||||
-rw-r--r-- | openbsc/include/openbsc/gsm_subscriber.h | 30 | ||||
-rw-r--r-- | openbsc/include/openbsc/iu.h | 61 | ||||
-rw-r--r-- | openbsc/include/openbsc/iu_cs.h | 7 | ||||
-rw-r--r-- | openbsc/include/openbsc/msc_api.h | 29 | ||||
-rw-r--r-- | openbsc/include/openbsc/msc_ifaces.h | 40 | ||||
-rw-r--r-- | openbsc/include/openbsc/signal.h | 1 | ||||
-rw-r--r-- | openbsc/include/openbsc/vty.h | 8 | ||||
-rw-r--r-- | openbsc/include/openbsc/xsc.h | 23 |
20 files changed, 388 insertions, 56 deletions
diff --git a/openbsc/include/openbsc/Makefile.am b/openbsc/include/openbsc/Makefile.am index c272b14de..efb22b209 100644 --- a/openbsc/include/openbsc/Makefile.am +++ b/openbsc/include/openbsc/Makefile.am @@ -8,7 +8,7 @@ noinst_HEADERS = abis_nm.h abis_rsl.h db.h gsm_04_08.h gsm_data.h \ vty.h socket.h e1_config.h trau_upqueue.h token_auth.h \ handover_decision.h rrlp.h \ crc24.h gprs_llc.h gprs_gmm.h \ - gb_proxy.h gprs_sgsn.h sgsn.h \ + gb_proxy.h gprs_sgsn.h gsm_04_08_gprs.h sgsn.h \ auth.h osmo_msc.h bsc_msc.h bsc_nat.h \ osmo_bsc_rf.h osmo_bsc.h network_listen.h bsc_nat_sccp.h \ osmo_msc_data.h osmo_bsc_grace.h sms_queue.h abis_om2000.h \ @@ -18,7 +18,9 @@ noinst_HEADERS = abis_nm.h abis_rsl.h db.h gsm_04_08.h gsm_data.h \ gprs_gb_parse.h smpp.h meas_feed.h \ gprs_gsup_client.h bsc_msg_filter.h \ oap.h oap_messages.h \ - gtphub.h + gtphub.h \ + msc_api.h msc_ifaces.h iu.h iu_cs.h \ + xsc.h openbsc_HEADERS = gsm_04_08.h meas_rep.h bsc_api.h openbscdir = $(includedir)/openbsc diff --git a/openbsc/include/openbsc/bsc_api.h b/openbsc/include/openbsc/bsc_api.h index a3d12f23b..3a9311991 100644 --- a/openbsc/include/openbsc/bsc_api.h +++ b/openbsc/include/openbsc/bsc_api.h @@ -52,6 +52,4 @@ int gsm0808_page(struct gsm_bts *bts, unsigned int page_group, unsigned int mi_len, uint8_t *mi, int chan_type); int gsm0808_clear(struct gsm_subscriber_connection *conn); -struct llist_head *bsc_api_sub_connections(struct gsm_network *net); - #endif diff --git a/openbsc/include/openbsc/bss.h b/openbsc/include/openbsc/bss.h index 49df547a1..39957ab7c 100644 --- a/openbsc/include/openbsc/bss.h +++ b/openbsc/include/openbsc/bss.h @@ -1,11 +1,14 @@ #ifndef _BSS_H_ #define _BSS_H_ +#include <openbsc/xsc.h> + struct gsm_network; struct msgb; /* start and stop network */ -extern int bsc_bootstrap_network(int (*mncc_recv)(struct gsm_network *, struct msgb *), const char *cfg_file); +extern int bsc_network_init(mncc_recv_cb_t mncc_recv); +extern int bsc_network_configure(const char *cfg_file); extern int bsc_shutdown_net(struct gsm_network *net); /* register all supported BTS */ diff --git a/openbsc/include/openbsc/debug.h b/openbsc/include/openbsc/debug.h index 189ca476e..2c8479be2 100644 --- a/openbsc/include/openbsc/debug.h +++ b/openbsc/include/openbsc/debug.h @@ -34,6 +34,9 @@ enum { DSMPP, DFILTER, DGTPHUB, + DSUA, + DRANAP, + DIUCS, Debug_LastEntry, }; diff --git a/openbsc/include/openbsc/gprs_gmm.h b/openbsc/include/openbsc/gprs_gmm.h index 702b9b9d3..b4df65092 100644 --- a/openbsc/include/openbsc/gprs_gmm.h +++ b/openbsc/include/openbsc/gprs_gmm.h @@ -10,7 +10,9 @@ int gsm48_tx_gsm_act_pdp_rej(struct sgsn_mm_ctx *mm, uint8_t tid, int gsm48_tx_gsm_act_pdp_acc(struct sgsn_pdp_ctx *pdp); int gsm48_tx_gsm_deact_pdp_acc(struct sgsn_pdp_ctx *pdp); -int gsm0408_gprs_rcvmsg(struct msgb *msg, struct gprs_llc_llme *llme); +int gsm0408_gprs_rcvmsg_gb(struct msgb *msg, struct gprs_llc_llme *llme); +int gsm0408_gprs_rcvmsg_iu(struct msgb *msg, struct gprs_ra_id *ra_id, + uint16_t *sai); int gsm0408_gprs_force_reattach(struct sgsn_mm_ctx *mmctx); int gsm0408_gprs_force_reattach_oldmsg(struct msgb *msg); void gsm0408_gprs_access_granted(struct sgsn_mm_ctx *mmctx); diff --git a/openbsc/include/openbsc/gprs_sgsn.h b/openbsc/include/openbsc/gprs_sgsn.h index 898b7a514..28cbea5bd 100644 --- a/openbsc/include/openbsc/gprs_sgsn.h +++ b/openbsc/include/openbsc/gprs_sgsn.h @@ -23,7 +23,7 @@ struct gsm_subscriber; enum gsm48_gsm_cause; /* TS 04.08 4.1.3.3 GMM mobility management states on the network side */ -enum gprs_mm_state { +enum gprs_gmm_state { GMM_DEREGISTERED, /* 4.1.3.3.1.1 */ GMM_COMMON_PROC_INIT, /* 4.1.3.3.1.2 */ GMM_REGISTERED_NORMAL, /* 4.1.3.3.2.1 */ @@ -31,6 +31,16 @@ enum gprs_mm_state { GMM_DEREGISTERED_INIT, /* 4.1.3.3.1.4 */ }; +/* TS 23.060 6.1.1 and 6.1.2 Mobility management states A/Gb and Iu mode */ +enum gprs_pmm_state { + PMM_DETACHED, + PMM_CONNECTED, + PMM_IDLE, + MM_IDLE = PMM_DETACHED, + MM_READY = PMM_CONNECTED, + MM_STANDBY = PMM_IDLE, +}; + enum gprs_mm_ctr { GMM_CTR_PKTS_SIG_IN, GMM_CTR_PKTS_SIG_OUT, @@ -92,13 +102,32 @@ struct sgsn_ggsn_lookup { uint8_t ti; }; +enum sgsn_ran_type { + /* GPRS/EDGE via Gb */ + MM_CTX_T_GERAN_Gb, + /* UMTS via Iu */ + MM_CTX_T_UTRAN_Iu, + /* GPRS/EDGE via Iu */ + MM_CTX_T_GERAN_Iu, +}; + +struct service_info { + uint8_t type; + uint16_t pdp_status; +}; + +struct ue_conn_ctx; + /* According to TS 03.60, Table 5: SGSN MM and PDP Contexts */ /* Extended by 3GPP TS 23.060, Table 6: SGSN MM and PDP Contexts */ struct sgsn_mm_ctx { struct llist_head list; + enum sgsn_ran_type ran_type; + char imsi[GSM23003_IMSI_MAX_DIGITS+1]; - enum gprs_mm_state mm_state; + enum gprs_gmm_state mm_state; + enum gprs_pmm_state pmm_state; uint32_t p_tmsi; uint32_t p_tmsi_old; /* old P-TMSI before new is confirmed */ uint32_t p_tmsi_sig; @@ -106,10 +135,32 @@ struct sgsn_mm_ctx { /* Opt: Software Version Numbber / TS 23.195 */ char msisdn[GSM_EXTENSION_LENGTH]; struct gprs_ra_id ra; - uint16_t cell_id; - uint32_t cell_id_age; - uint16_t sac; /* Iu: Service Area Code */ - uint32_t sac_age;/* Iu: Service Area Code age */ + struct { + uint16_t cell_id; /* Gb only */ + uint32_t cell_id_age; /* Gb only */ + uint8_t radio_prio_sms; + + /* Additional bits not present in the GSM TS */ + uint16_t nsei; + uint16_t bvci; + struct gprs_llc_llme *llme; + uint32_t tlli; + uint32_t tlli_new; + } gb; + struct { + int new_key; + uint16_t sac; /* Iu: Service Area Code */ + uint32_t sac_age; /* Iu: Service Area Code age */ + /* CSG ID */ + /* CSG Membership */ + /* Access Mode */ + /* Seelected CN Operator ID (TS 23.251) */ + /* CSG Subscription Data */ + /* LIPA Allowed */ + /* Voice Support Match Indicator */ + struct ue_conn_ctx *ue_ctx; + struct service_info service; + } iu; /* VLR number */ uint32_t new_sgsn_addr; /* Authentication Triplet */ @@ -118,30 +169,38 @@ struct sgsn_mm_ctx { /* Iu: CK, IK, KSI */ /* CKSN */ enum gprs_ciph_algo ciph_algo; + struct { uint8_t len; uint8_t buf[50]; /* GSM 04.08 10.5.5.12a, extended in TS 24.008 */ } ms_radio_access_capa; + /* Supported Codecs (SRVCC) */ struct { uint8_t len; uint8_t buf[8]; /* GSM 04.08 10.5.5.12, extended in TS 24.008 */ } ms_network_capa; + /* UE Netowrk Capability (E-UTRAN) */ uint16_t drx_parms; + /* Active Time value for PSM */ int mnrg; /* MS reported to HLR? */ int ngaf; /* MS reported to MSC/VLR? */ int ppf; /* paging for GPRS + non-GPRS? */ + /* Subscribed Charging Characteristics */ + /* Trace Reference */ + /* Trace Type */ + /* Trigger ID */ + /* OMC Identity */ /* SMS Parameters */ int recovery; - uint8_t radio_prio_sms; + /* Access Restriction */ + /* GPRS CSI (CAMEL) */ + /* MG-CSI (CAMEL) */ + /* Subscribed UE-AMBR */ + /* UE-AMBR */ + /* APN Subscribed */ struct llist_head pdp_list; - /* Additional bits not present in the GSM TS */ - struct gprs_llc_llme *llme; - uint32_t tlli; - uint32_t tlli_new; - uint16_t nsei; - uint16_t bvci; struct rate_ctr_group *ctrg; struct osmo_timer_list timer; unsigned int T; /* Txxxx number */ @@ -176,6 +235,7 @@ struct sgsn_mm_ctx *sgsn_mm_ctx_by_tlli(uint32_t tlli, const struct gprs_ra_id *raid); struct sgsn_mm_ctx *sgsn_mm_ctx_by_ptmsi(uint32_t tmsi); struct sgsn_mm_ctx *sgsn_mm_ctx_by_imsi(const char *imsi); +struct sgsn_mm_ctx *sgsn_mm_ctx_by_ue_ctx(const void *uectx); /* look-up by matching TLLI and P-TMSI (think twice before using this) */ struct sgsn_mm_ctx *sgsn_mm_ctx_by_tlli_and_ptmsi(uint32_t tlli, @@ -184,6 +244,8 @@ struct sgsn_mm_ctx *sgsn_mm_ctx_by_tlli_and_ptmsi(uint32_t tlli, /* Allocate a new SGSN MM context */ struct sgsn_mm_ctx *sgsn_mm_ctx_alloc(uint32_t tlli, const struct gprs_ra_id *raid); +struct sgsn_mm_ctx *sgsn_mm_ctx_alloc_iu(void *uectx); + void sgsn_mm_ctx_cleanup_free(struct sgsn_mm_ctx *ctx); struct sgsn_ggsn_ctx *sgsn_mm_ctx_find_ggsn_ctx(struct sgsn_mm_ctx *mmctx, diff --git a/openbsc/include/openbsc/gsm_04_08.h b/openbsc/include/openbsc/gsm_04_08.h index fd0b89d79..156605487 100644 --- a/openbsc/include/openbsc/gsm_04_08.h +++ b/openbsc/include/openbsc/gsm_04_08.h @@ -77,6 +77,8 @@ int decode_bcd_number(char *output, int output_len, const uint8_t *bcd_lv, int send_siemens_mrpci(struct gsm_lchan *lchan, uint8_t *classmark2_lv); int gsm48_extract_mi(uint8_t *classmark2, int length, char *mi_string, uint8_t *mi_type); int gsm48_paging_extract_mi(struct gsm48_pag_resp *pag, int length, char *mi_string, uint8_t *mi_type); + +/* TODO MSCSPLIT remove gsm48_handle_paging_resp() */ int gsm48_handle_paging_resp(struct gsm_subscriber_connection *conn, struct msgb *msg, struct gsm_subscriber *subscr); int gsm48_lchan_modify(struct gsm_lchan *lchan, uint8_t lchan_mode); diff --git a/openbsc/include/openbsc/gsm_04_08_gprs.h b/openbsc/include/openbsc/gsm_04_08_gprs.h new file mode 100644 index 000000000..42b9a795e --- /dev/null +++ b/openbsc/include/openbsc/gsm_04_08_gprs.h @@ -0,0 +1,21 @@ +#pragma once + +#include <osmocom/gsm/protocol/gsm_04_08_gprs.h> + +/* TODO: Move this to osmocom/gsm/protocol/gsm_04_08_gprs.h ? */ + +/* Table 10.4 in 3GPP TS 24.008 (successor to 04.08) */ +#define GSM48_MT_GMM_SERVICE_REQ 0x0c +#define GSM48_MT_GMM_SERVICE_ACK 0x0d +#define GSM48_MT_GMM_SERVICE_REJ 0x0e + +/* 3GPP 24.008 / Chapter 10.5.5.20 / Table 10.5.153a */ +enum gsm48_gmm_service_type { + GPRS_SERVICE_T_SIGNALLING = 0x00, + GPRS_SERVICE_T_DATA = 0x01, + GPRS_SERVICE_T_PAGING_RESP = 0x02, + GPRS_SERVICE_T_MBMS_MC_SERV = 0x03, + GPRS_SERVICE_T_MBMS_BC_SERV = 0x04, +}; + +extern const struct value_string *gprs_service_t_strs; diff --git a/openbsc/include/openbsc/gsm_04_11.h b/openbsc/include/openbsc/gsm_04_11.h index 00c3a19fa..149de9083 100644 --- a/openbsc/include/openbsc/gsm_04_11.h +++ b/openbsc/include/openbsc/gsm_04_11.h @@ -38,5 +38,5 @@ int gsm411_send_sms(struct gsm_subscriber_connection *conn, struct gsm_sms *sms); void gsm411_sapi_n_reject(struct gsm_subscriber_connection *conn); -uint8_t sms_next_rp_msg_ref(struct gsm_subscriber_connection *conn); +uint8_t sms_next_rp_msg_ref(uint8_t *next_rp_ref); #endif diff --git a/openbsc/include/openbsc/gsm_04_80.h b/openbsc/include/openbsc/gsm_04_80.h index 0a6065234..23f20c463 100644 --- a/openbsc/include/openbsc/gsm_04_80.h +++ b/openbsc/include/openbsc/gsm_04_80.h @@ -14,6 +14,9 @@ int gsm0480_send_ussd_reject(struct gsm_subscriber_connection *conn, const struct msgb *msg, const struct ussd_request *request); +struct msgb *gsm0480_gen_ussdNotify(int level, const char *text); +struct msgb *gsm0480_gen_releaseComplete(void); + int gsm0480_send_ussdNotify(struct gsm_subscriber_connection *conn, int level, const char *text); int gsm0480_send_releaseComplete(struct gsm_subscriber_connection *conn); diff --git a/openbsc/include/openbsc/gsm_data.h b/openbsc/include/openbsc/gsm_data.h index f229e7499..44a83117e 100644 --- a/openbsc/include/openbsc/gsm_data.h +++ b/openbsc/include/openbsc/gsm_data.h @@ -8,6 +8,7 @@ #include <osmocom/crypt/auth.h> #include <openbsc/rest_octets.h> +#include <openbsc/xsc.h> /** annotations for msgb ownership */ #define __uses @@ -97,7 +98,19 @@ struct neigh_meas_proc { uint8_t last_seen_nr; }; -/* the per subscriber data for lchan */ +enum interface_type { + IFACE_UNKNOWN = -1, + IFACE_A = 0, /* A-interface for 2G */ + IFACE_IU = 1 /* Iu-interface for UMTS aka 3G (IuCS or IuPS) */ +}; + +enum integrity_protection_state { + INTEGRITY_PROTECTION_NONE = 0, + INTEGRITY_PROTECTION_IK = 1, + INTEGRITY_PROTECTION_IK_CK = 2, +}; + +/* mobile subscriber data */ struct gsm_subscriber_connection { struct llist_head entry; @@ -124,18 +137,40 @@ struct gsm_subscriber_connection { int mncc_rtp_create_pending; int mncc_rtp_connect_pending; - /* bsc structures */ - struct osmo_bsc_sccp_con *sccp_con; - /* back pointers */ + struct gsm_network *network; + + /* The BSC used to be an integral part of OsmoNITB. In OsmoCSCN, the + * BSC and/or RNC is a separate entity, and no back pointers to the bts + * and lchan structures are available. To facilitate separation of the + * code paths, I'm explicitly excluding the unavailable structures from + * the build. Once separated, this split may become unnecessary. */ +#if COMPILING_LIBMSC int in_release; + uint16_t lac; + struct gsm_encr encr; + + /* 2G or 3G? See enum interface_type */ + int via_iface; + + /* which Iu-CS connection, if any. */ + struct { + struct ue_conn_ctx *ue_ctx; + int integrity_protection; + } iu; + +#else + struct gsm_bts *bts; struct gsm_lchan *lchan; struct gsm_lchan *ho_lchan; - struct gsm_bts *bts; + + /* bsc structures */ + struct osmo_bsc_sccp_con *sccp_con; /* for assignment handling */ struct osmo_timer_list T10; struct gsm_lchan *secondary_lchan; +#endif }; @@ -207,7 +242,20 @@ enum gsm_auth_policy { #define GSM_T3113_DEFAULT 60 #define GSM_T3122_DEFAULT 10 +struct gsm_tz { + int override; /* if 0, use system's time zone instead. */ + int hr; /* hour */ + int mn; /* minute */ + int dst; /* daylight savings */ +}; + struct gsm_network { + /* TODO MSCSPLIT the gsm_network struct is basically a kitchen sink for + * global settings and variables, "madly" mixing BSC and MSC stuff. Split + * this in e.g. struct osmo_bsc and struct osmo_msc, with the things + * these have in common, like country and network code, put in yet + * separate structs and placed as members in osmo_bsc and osmo_msc. */ + /* global parameters */ uint16_t country_code; uint16_t network_code; @@ -290,6 +338,19 @@ struct gsm_network { /* control interface */ struct ctrl_handle *ctrl; + + /* all active subscriber connections. */ + struct llist_head subscr_conns; + + /* if override is nonzero, this timezone data is used for all MM + * contexts. */ + /* TODO: in OsmoNITB, tz-override used to be BTS-specific. To enable + * BTS|RNC specific timezone overrides for multi-tz networks in + * OsmoCSCN, this should be tied to the location area code (LAC). */ + struct gsm_tz tz; + + /* Periodic location update default value */ + uint8_t t3212; }; struct osmo_esme; @@ -336,13 +397,12 @@ struct gsm_sms { char text[SMS_TEXT_SIZE]; }; -struct gsm_network *gsm_network_init(uint16_t country_code, uint16_t network_code, - int (*mncc_recv)(struct gsm_network *, struct msgb *)); -int gsm_set_bts_type(struct gsm_bts *bts, enum gsm_bts_type type); +struct gsm_network *gsm_network_init(void *ctx, + uint16_t country_code, + uint16_t network_code, + mncc_recv_cb_t mncc_recv); -/* Get reference to a neighbor cell on a given BCCH ARFCN */ -struct gsm_bts *gsm_bts_neighbor(const struct gsm_bts *bts, - uint16_t arfcn, uint8_t bsic); +int gsm_set_bts_type(struct gsm_bts *bts, enum gsm_bts_type type); enum gsm_bts_type parse_btstype(const char *arg); const char *btstype2str(enum gsm_bts_type type); @@ -426,13 +486,15 @@ int bts_gprs_mode_is_compat(struct gsm_bts *bts, enum bts_gprs_mode mode); int gsm48_ra_id_by_bts(uint8_t *buf, struct gsm_bts *bts); void gprs_ra_id_by_bts(struct gprs_ra_id *raid, struct gsm_bts *bts); -struct gsm_meas_rep *lchan_next_meas_rep(struct gsm_lchan *lchan); int gsm_btsmodel_set_feature(struct gsm_bts_model *model, enum gsm_bts_features feat); int gsm_bts_model_register(struct gsm_bts_model *model); -struct gsm_subscriber_connection *subscr_con_allocate(struct gsm_lchan *lchan); -void subscr_con_free(struct gsm_subscriber_connection *conn); +struct gsm_subscriber_connection *bsc_subscr_con_allocate(struct gsm_lchan *lchan); +void bsc_subscr_con_free(struct gsm_subscriber_connection *conn); + +struct gsm_subscriber_connection *msc_subscr_con_allocate(struct gsm_network *network); +void msc_subscr_con_free(struct gsm_subscriber_connection *conn); struct gsm_bts *gsm_bts_alloc_register(struct gsm_network *net, enum gsm_bts_type type, diff --git a/openbsc/include/openbsc/gsm_data_shared.h b/openbsc/include/openbsc/gsm_data_shared.h index 8658fe717..5643d48e6 100644 --- a/openbsc/include/openbsc/gsm_data_shared.h +++ b/openbsc/include/openbsc/gsm_data_shared.h @@ -24,6 +24,8 @@ #include <osmocom/gsm/lapdm.h> #endif +#include <openbsc/xsc.h> + struct osmo_bsc_data; struct osmo_bsc_sccp_con; @@ -100,7 +102,6 @@ struct gsm_abis_mo { struct gsm_bts *bts; }; -#define MAX_A5_KEY_LEN (128/8) #define A38_XOR_MIN_KEY_LEN 12 #define A38_XOR_MAX_KEY_LEN 16 #define A38_COMP128_KEY_LEN 16 @@ -202,11 +203,7 @@ struct gsm_lchan { uint8_t bs_power; uint8_t ms_power; /* Encryption information */ - struct { - uint8_t alg_id; - uint8_t key_len; - uint8_t key[MAX_A5_KEY_LEN]; - } encr; + struct gsm_encr encr; /* AMR bits */ uint8_t mr_ms_lv[7]; @@ -351,7 +348,7 @@ struct gsm_bts_trx_ts { struct gsm_lchan lchan[TS_MAX_LCHAN]; }; -/* One TRX in a BTS */ +/* One TRX (transceiver) in a BTS */ struct gsm_bts_trx { /* list header in bts->trx_list */ struct llist_head list; @@ -609,14 +606,6 @@ struct gsm_bts { /* buffers where we put the pre-computed SI */ sysinfo_buf_t si_buf[_MAX_SYSINFO_TYPE]; - /* TimeZone hours, mins, and bts specific */ - struct { - int hr; - int mn; - int override; - int dst; - } tz; - /* ip.accesss Unit ID's have Site/BTS/TRX layout */ union { struct { diff --git a/openbsc/include/openbsc/gsm_subscriber.h b/openbsc/include/openbsc/gsm_subscriber.h index 9df989a79..44e24b03c 100644 --- a/openbsc/include/openbsc/gsm_subscriber.h +++ b/openbsc/include/openbsc/gsm_subscriber.h @@ -1,6 +1,8 @@ #ifndef _GSM_SUBSCR_H #define _GSM_SUBSCR_H +#include <stdbool.h> + #include "gsm_data.h" #include <osmocom/core/linuxlist.h> #include <osmocom/gsm/protocol/gsm_23_003.h> @@ -68,6 +70,7 @@ struct gsm_subscriber { /* pending requests */ int is_paging; + struct osmo_timer_list paging_timeout; struct llist_head requests; /* GPRS/SGSN related fields */ @@ -87,6 +90,20 @@ enum gsm_subscriber_update_reason { GSM_SUBSCRIBER_UPDATE_EQUIPMENT, }; +/* + * Struct for pending channel requests. This is managed in the + * llist_head requests of each subscriber. The reference counting + * should work in such a way that a subscriber with a pending request + * remains in memory. + */ +struct subscr_request { + struct llist_head entry; + + /* the callback data */ + gsm_cbfn *cbfn; + void *param; +}; + struct gsm_subscriber *subscr_get(struct gsm_subscriber *subscr); struct gsm_subscriber *subscr_put(struct gsm_subscriber *subscr); struct gsm_subscriber *subscr_create_subscriber(struct gsm_subscriber_group *sgrp, @@ -101,7 +118,8 @@ struct gsm_subscriber *subscr_get_by_id(struct gsm_subscriber_group *sgrp, unsigned long long id); struct gsm_subscriber *subscr_get_or_create(struct gsm_subscriber_group *sgrp, const char *imsi); -int subscr_update(struct gsm_subscriber *s, struct gsm_bts *bts, int reason); +int subscr_update(struct gsm_network *network, struct gsm_subscriber *s, + uint16_t lac, int reason); struct gsm_subscriber *subscr_active_by_tmsi(struct gsm_subscriber_group *sgrp, uint32_t tmsi); struct gsm_subscriber *subscr_active_by_imsi(struct gsm_subscriber_group *sgrp, @@ -112,14 +130,18 @@ char *subscr_name(struct gsm_subscriber *subscr); int subscr_purge_inactive(struct gsm_subscriber_group *sgrp); void subscr_update_from_db(struct gsm_subscriber *subscr); void subscr_expire(struct gsm_subscriber_group *sgrp); -int subscr_update_expire_lu(struct gsm_subscriber *subscr, struct gsm_bts *bts); +int subscr_update_expire_lu(struct gsm_network *network, struct gsm_subscriber *subscr); + +bool subscr_authorized(struct gsm_subscriber *subsc); /* * Paging handling with authentication */ -struct subscr_request *subscr_request_channel(struct gsm_subscriber *subscr, - int type, gsm_cbfn *cbfn, void *param); +struct subscr_request *subscr_request_conn(struct gsm_subscriber *subscr, + gsm_cbfn *cbfn, void *param); void subscr_remove_request(struct subscr_request *req); +int subscr_rx_paging_response(struct msgb *msg, + struct gsm_subscriber_connection *conn); /* internal */ struct gsm_subscriber *subscr_alloc(void); diff --git a/openbsc/include/openbsc/iu.h b/openbsc/include/openbsc/iu.h new file mode 100644 index 000000000..d5b9135de --- /dev/null +++ b/openbsc/include/openbsc/iu.h @@ -0,0 +1,61 @@ +#pragma once + +#include <stdbool.h> + +struct sgsn_pdp_ctx; +struct msgb; +struct gprs_ra_id; + +struct RANAP_RAB_SetupOrModifiedItemIEs_s; +struct RANAP_GlobalRNC_ID; + +struct ue_conn_ctx { + struct llist_head list; + struct osmo_sua_link *link; + uint32_t conn_id; + int integrity_active; + struct gprs_ra_id ra_id; +}; + +enum iu_event_type { + IU_EVENT_RAB_ASSIGN, + IU_EVENT_SECURITY_MODE_COMPLETE, + IU_EVENT_IU_RELEASE, /* An actual Iu Release message was received */ + IU_EVENT_LINK_INVALIDATED, /* A SUA link was lost or closed down */ + /* FIXME: maybe IU_EVENT_IU_RELEASE and IU_EVENT_LINK_INVALIDATED + * should be combined to one generic event that simply means the + * ue_conn_ctx should no longer be used, for whatever reason. */ +}; + +extern const struct value_string iu_event_type_names[]; +static inline const char *iu_event_type_str(enum iu_event_type e) +{ + return get_value_string(iu_event_type_names, e); +} + +/* Implementations of iu_recv_cb_t shall find the ue_conn_ctx in msg->dst. */ +typedef int (* iu_recv_cb_t )(struct msgb *msg, struct gprs_ra_id *ra_id, + /* TODO "gprs_" in generic CS+PS domain ^ */ + uint16_t *sai); + +typedef int (* iu_event_cb_t )(struct ue_conn_ctx *ue_ctx, + enum iu_event_type type, void *data); + +typedef int (* iu_rab_ass_resp_cb_t )(struct ue_conn_ctx *ue_ctx, uint8_t rab_id, + struct RANAP_RAB_SetupOrModifiedItemIEs_s *setup_ies); + +int iu_init(void *ctx, const char *listen_addr, uint16_t listen_port, + iu_recv_cb_t iu_recv_cb, iu_event_cb_t iu_event_cb); + +void iu_link_del(struct osmo_sua_link *link); + +int iu_tx(struct msgb *msg, uint8_t sapi); + +int iu_page_cs(const char *imsi, const uint32_t *tmsi, uint16_t lac); +int iu_page_ps(const char *imsi, const uint32_t *ptmsi, uint16_t lac, uint8_t rac); + +int iu_rab_act_cs(struct ue_conn_ctx *ue_ctx, uint32_t rtp_ip, uint16_t rtp_port); +int iu_rab_act_ps(uint8_t rab_id, struct sgsn_pdp_ctx *pdp, bool use_x213_nsap); +int iu_rab_deact(struct ue_conn_ctx *ue_ctx, uint8_t rab_id); +int iu_tx_sec_mode_cmd(struct ue_conn_ctx *uectx, struct gsm_auth_tuple *tp, + int send_ck, int new_key); diff --git a/openbsc/include/openbsc/iu_cs.h b/openbsc/include/openbsc/iu_cs.h new file mode 100644 index 000000000..fb61a5cf1 --- /dev/null +++ b/openbsc/include/openbsc/iu_cs.h @@ -0,0 +1,7 @@ +#pragma once + +int gsm0408_rcvmsg_iucs(struct gsm_network *network, struct msgb *msg, + uint16_t *lac); + +struct gsm_subscriber_connection *subscr_conn_lookup_iu(struct gsm_network *network, + struct ue_conn_ctx *ue); diff --git a/openbsc/include/openbsc/msc_api.h b/openbsc/include/openbsc/msc_api.h new file mode 100644 index 000000000..b0197386c --- /dev/null +++ b/openbsc/include/openbsc/msc_api.h @@ -0,0 +1,29 @@ +#pragma once + +/* These functions receive or send MM|CC|... messages from/to the BSC|RNC + * direction, while they are not concerned with which particular external + * interface is actually involved (A or IuCS). + * + * For the interface specific decisions see msc_iface.[hc] + */ + +/* MSCSPLIT WIP: this will gradually replace the role that the bsc_api.h had in + * OsmoNITB. Actually, osmo_msc.[hc] has the same role as this file, but having + * separate files helps me to keep track of how far I've gotten yet. */ + +#include <stdint.h> + +struct gsm_subscriber_connection; +struct msgb; + +enum { + MSC_CONN_ACCEPT = 0, + MSC_CONN_REJECT = 1, +}; + +/* receive a Level 3 Complete message and return MSC_CONN_ACCEPT or + * MSC_CONN_REJECT */ +int msc_compl_l3(struct gsm_subscriber_connection *conn, struct msgb *msg, + uint16_t chosen_channel); +/* TODO: is chosen_channel BSC land == NITB legacy? */ + diff --git a/openbsc/include/openbsc/msc_ifaces.h b/openbsc/include/openbsc/msc_ifaces.h new file mode 100644 index 000000000..57d16f4e4 --- /dev/null +++ b/openbsc/include/openbsc/msc_ifaces.h @@ -0,0 +1,40 @@ +#pragma once + +#include <osmocom/core/msgb.h> +#include <openbsc/gsm_data.h> + +/* These are the interfaces of the MSC layer towards (from?) the BSC and RNC, + * i.e. in the direction towards the mobile device (MS aka UE). + * + * 2G will use the A-interface, + * 3G aka UMTS will use the Iu-interface (for the MSC, it's IuCS). + * + * To allow linking parts of the MSC code without having to include entire + * infrastructures of external libraries, the core transmitting and receiving + * functions are left unimplemented. For example, a unit test does not need to + * link against external ASN1 libraries if it is never going to encode actual + * outgoing messages. It is up to each building scope to implement real world + * functions or to plug mere dummy implementations. + * + * For example, msc_tx_dtap(conn, msg), depending on conn->via_iface, will call + * either iu_tx() or a_tx() [note: at time of writing, the A-interface is not + * yet implemented]. When you try to link against libmsc, you will find that + * the compiler complains about an undefined reference to iu_tx(). If you, + * however, link against libiu as well as the osmo-iuh libs (etc.), iu_tx() is + * available. A unit test may instead simply implement a dummy iu_tx() function + * and not link against osmo-iuh. + */ + +/* Each main linkage must implement this function (see comment above). */ +extern int iu_tx(struct msgb *msg, uint8_t sapi); + +/* So far this is a dummy implemented in libmsc/a_iface.c. When A-interface + * gets implemented, it should be in a separate lib (like libiu), this function + * should move there, and the following comment should remain here: " + * Each main linkage must implement this function (see comment above). + * " */ +extern int a_tx(struct msgb *msg); + +int msc_tx_dtap(struct gsm_subscriber_connection *conn, + struct msgb *msg); + diff --git a/openbsc/include/openbsc/signal.h b/openbsc/include/openbsc/signal.h index 8f27b3831..f3fad4e70 100644 --- a/openbsc/include/openbsc/signal.h +++ b/openbsc/include/openbsc/signal.h @@ -142,7 +142,6 @@ struct gsm_subscriber; struct paging_signal_data { struct gsm_subscriber *subscr; - struct gsm_bts *bts; int paging_result; diff --git a/openbsc/include/openbsc/vty.h b/openbsc/include/openbsc/vty.h index bc30e2357..1d8f8712d 100644 --- a/openbsc/include/openbsc/vty.h +++ b/openbsc/include/openbsc/vty.h @@ -32,18 +32,22 @@ enum bsc_vty_node { TRUNK_NODE, PGROUP_NODE, MNCC_INT_NODE, - NITB_NODE, BSC_NODE, SMPP_NODE, SMPP_ESME_NODE, GTPHUB_NODE, + CSCN_NODE, }; extern int bsc_vty_is_config_node(struct vty *vty, int node); extern void bsc_replace_string(void *ctx, char **dst, const char *newstr); struct log_info; -int bsc_vty_init(const struct log_info *cat); +int bsc_vty_init(const struct log_info *cat, struct gsm_network *network); int bsc_vty_init_extra(void); +void cscn_vty_init(void); + +struct gsm_network *gsmnet_from_vty(struct vty *vty); + #endif diff --git a/openbsc/include/openbsc/xsc.h b/openbsc/include/openbsc/xsc.h new file mode 100644 index 000000000..b301d5018 --- /dev/null +++ b/openbsc/include/openbsc/xsc.h @@ -0,0 +1,23 @@ +#pragma once + +#include <stdint.h> + +struct msgb; +struct gsm_network; +struct log_info; +struct ctrl_handle; + +typedef int (*mncc_recv_cb_t)(struct gsm_network *, struct msgb *); + +#define MAX_A5_KEY_LEN (128/8) + +struct gsm_encr { + uint8_t alg_id; + uint8_t key_len; + uint8_t key[MAX_A5_KEY_LEN]; +}; + +extern struct gsm_network *vty_global_gsm_network; + +int xsc_vty_init(struct gsm_network *network); + |