diff --git a/libpri.h b/libpri.h index c8efc26..f71ee29 100644 --- a/libpri.h +++ b/libpri.h @@ -183,6 +183,10 @@ #define PRES_NUMBER_NOT_AVAILABLE \ (PRI_PRES_UNAVAILABLE | PRI_PRES_NETWORK_NUMBER) +/* Reverse Charging Indication */ +#define PRI_REVERSECHARGE_NONE -1 +#define PRI_REVERSECHARGE_REQUESTED 1 + /* Causes for disconnection */ #define PRI_CAUSE_UNALLOCATED 1 #define PRI_CAUSE_NO_ROUTE_TRANSIT_NET 2 /* !Q.SIG */ @@ -643,6 +647,7 @@ int pri_sr_set_redirecting(struct pri_sr *sr, char *num, int plan, int pres, int #define PRI_USER_USER_TX /* Set the user user field. Warning! don't send binary data accross this field */ void pri_sr_set_useruser(struct pri_sr *sr, const char *userchars); +void pri_sr_set_reversecharge(struct pri_sr *sr, int requested); void pri_call_set_useruser(q931_call *sr, const char *userchars); @@ -709,7 +714,6 @@ void pri_enslave(struct pri *master, struct pri *slave); #define PRI_REDIRECTING_REASON #define PRI_AOC_UNITS #define PRI_ANI -#define PRI_REVERSECHARGE_SUPPORT /* Send notification */ int pri_notify(struct pri *pri, q931_call *c, int channel, int info); diff --git a/pri.c b/pri.c index 11ee8f0..de84033 100644 --- a/pri.c +++ b/pri.c @@ -692,7 +692,7 @@ void pri_dump_event(struct pri *pri, pri_event *e) static void pri_sr_init(struct pri_sr *req) { memset(req, 0, sizeof(struct pri_sr)); - + req->reversecharge = PRI_REVERSECHARGE_NONE; } int pri_sr_set_connection_call_independent(struct pri_sr *req) @@ -961,3 +961,8 @@ int pri_sr_set_redirecting(struct pri_sr *sr, char *num, int plan, int pres, int sr->redirectingreason = reason; return 0; } + +void pri_sr_set_reversecharge(struct pri_sr *sr, int requested) +{ + sr->reversecharge = requested; +} diff --git a/pri_internal.h b/pri_internal.h index 000818d..8c8ff71 100644 --- a/pri_internal.h +++ b/pri_internal.h @@ -156,6 +156,7 @@ struct pri_sr { int justsignalling; const char *useruserinfo; int transferable; + int reversecharge; }; /* Internal switch types */ @@ -272,7 +273,10 @@ struct q931_call { q931_call *bridged_call; /* Pointer to other leg of bridged call (Used by Q.SIG when eliminating tromboned calls) */ int changestatus; /* SERVICE message changestatus */ - int reversecharge; /* Reverse charging indication */ + int reversecharge; /* Reverse charging indication: + -1 - No reverse charging + 1 - Reverse charging + 0,2-7 - Reserved for future use */ }; extern int pri_schedule_event(struct pri *pri, int ms, void (*function)(void *data), void *data); diff --git a/q931.c b/q931.c index d3a93b0..5553d4b 100644 --- a/q931.c +++ b/q931.c @@ -2154,6 +2154,15 @@ static int receive_reverse_charging_indication(int full_ie, struct pri *ctrl, q9 return 0; } +static int transmit_reverse_charging_indication(int full_ie, struct pri *ctrl, q931_call *call, int msgtype, q931_ie *ie, int len, int order) +{ + if (call->reversecharge != PRI_REVERSECHARGE_NONE) { + ie->data[0] = 0x80 | (call->reversecharge & 0x7); + return 3; + } + return 0; +} + static struct ie ies[] = { /* Codeset 0 - Common */ { 1, NATIONAL_CHANGE_STATUS, "Change Status", dump_change_status, receive_change_status, transmit_change_status }, @@ -2170,7 +2179,7 @@ static struct ie ies[] = { { 1, Q931_BINARY_PARAMETERS, "Packet-layer Binary Parameters" }, { 1, Q931_WINDOW_SIZE, "Packet-layer Window Size" }, { 1, Q931_CLOSED_USER_GROUP, "Closed User Group" }, - { 1, Q931_REVERSE_CHARGE_INDIC, "Reverse Charging Indication", dump_reverse_charging_indication, receive_reverse_charging_indication }, + { 1, Q931_REVERSE_CHARGE_INDIC, "Reverse Charging Indication", dump_reverse_charging_indication, receive_reverse_charging_indication, transmit_reverse_charging_indication }, { 1, Q931_CALLING_PARTY_NUMBER, "Calling Party Number", dump_calling_party_number, receive_calling_party_number, transmit_calling_party_number }, { 1, Q931_CALLING_PARTY_SUBADDR, "Calling Party Subaddress", dump_calling_party_subaddr, receive_calling_party_subaddr }, { 1, Q931_CALLED_PARTY_NUMBER, "Called Party Number", dump_called_party_number, receive_called_party_number, transmit_called_party_number }, @@ -3116,8 +3125,8 @@ int q931_disconnect(struct pri *ctrl, q931_call *c, int cause) } static int setup_ies[] = { Q931_BEARER_CAPABILITY, Q931_CHANNEL_IDENT, Q931_IE_FACILITY, Q931_PROGRESS_INDICATOR, Q931_NETWORK_SPEC_FAC, Q931_DISPLAY, - Q931_CALLING_PARTY_NUMBER, Q931_CALLED_PARTY_NUMBER, Q931_REDIRECTING_NUMBER, Q931_IE_USER_USER, Q931_SENDING_COMPLETE, - Q931_IE_ORIGINATING_LINE_INFO, Q931_IE_GENERIC_DIGITS, -1 }; + Q931_REVERSE_CHARGE_INDIC, Q931_CALLING_PARTY_NUMBER, Q931_CALLED_PARTY_NUMBER, Q931_REDIRECTING_NUMBER, Q931_IE_USER_USER, + Q931_SENDING_COMPLETE, Q931_IE_ORIGINATING_LINE_INFO, Q931_IE_GENERIC_DIGITS, -1 }; static int gr303_setup_ies[] = { Q931_BEARER_CAPABILITY, Q931_CHANNEL_IDENT, -1 }; @@ -3206,6 +3215,8 @@ int q931_setup(struct pri *ctrl, q931_call *c, struct pri_sr *req) else c->progressmask = 0; + c->reversecharge = req->reversecharge; + pri_call_add_standard_apdus(ctrl, c); if (ctrl->subchannel && !ctrl->bri) @@ -3445,6 +3456,7 @@ static int prepare_to_handle_q931_message(struct pri *ctrl, q931_mh *mh, q931_ca c->complete = 0; c->nonisdn = 0; c->aoc_units = -1; + c->reversecharge = -1; /* Fall through */ case Q931_CONNECT: case Q931_ALERTING: