From 74b55a890e5c62c35144abba179b7679a79ea8f4 Mon Sep 17 00:00:00 2001 From: Michael Jerris Date: Thu, 24 May 2007 04:12:15 +0000 Subject: [PATCH] add initial National ISDN Dialect. git-svn-id: http://svn.openzap.org/svn/openzap/trunk@132 a93c3328-9c30-0410-af19-c9cd2b2d52af --- libs/openzap/openzap.vcproj | 20 ++ libs/openzap/src/isdn/Q931.c | 7 + libs/openzap/src/isdn/Q931ie.c | 3 +- libs/openzap/src/isdn/include/Q931.h | 3 +- libs/openzap/src/isdn/nationalStateNT.c | 126 ++++++++++ libs/openzap/src/isdn/nationalStateTE.c | 210 +++++++++++++++++ libs/openzap/src/isdn/nationalie.c | 254 ++++++++++++++++++++ libs/openzap/src/isdn/nationalmes.c | 301 ++++++++++++++++++++++++ 8 files changed, 921 insertions(+), 3 deletions(-) create mode 100644 libs/openzap/src/isdn/nationalStateNT.c create mode 100644 libs/openzap/src/isdn/nationalStateTE.c create mode 100644 libs/openzap/src/isdn/nationalie.c create mode 100644 libs/openzap/src/isdn/nationalmes.c diff --git a/libs/openzap/openzap.vcproj b/libs/openzap/openzap.vcproj index af00754f66..aaacf7578b 100644 --- a/libs/openzap/openzap.vcproj +++ b/libs/openzap/openzap.vcproj @@ -368,6 +368,22 @@ RelativePath=".\src\isdn\mfifo.c" > + + + + + + + + @@ -407,6 +423,10 @@ RelativePath=".\src\isdn\include\mfifo.h" > + + diff --git a/libs/openzap/src/isdn/Q931.c b/libs/openzap/src/isdn/Q931.c index f230b5973a..0e130a3668 100644 --- a/libs/openzap/src/isdn/Q931.c +++ b/libs/openzap/src/isdn/Q931.c @@ -37,6 +37,7 @@ *****************************************************************************/ #include "Q931.h" +#include "national.h" /***************************************************************************** @@ -253,6 +254,12 @@ void Q931Initialize() if(Q931CreateDialectCB[Q931_Dialect_Q931 + Q931_NT] == NULL) Q931AddDialect(Q931_Dialect_Q931 + Q931_NT, Q931CreateNT); + if(Q931CreateDialectCB[Q931_Dialect_National + Q931_TE] == NULL) + Q931AddDialect(Q931_Dialect_National + Q931_TE, nationalCreateTE); + + if(Q931CreateDialectCB[Q931_Dialect_National + Q931_NT] == NULL) + Q931AddDialect(Q931_Dialect_National + Q931_NT, nationalCreateNT); + /* The last step we do is to call the callbacks to create the dialects */ for(x=0; x< Q931MAXDLCT; x++) { diff --git a/libs/openzap/src/isdn/Q931ie.c b/libs/openzap/src/isdn/Q931ie.c index f6d29610d9..1435e3abc7 100644 --- a/libs/openzap/src/isdn/Q931ie.c +++ b/libs/openzap/src/isdn/Q931ie.c @@ -819,8 +819,7 @@ L3INT Q931Uie_CallingNum(Q931_TrunkInfo_t *pTrunk, ie *pIE, L3UCHAR * IBuf, L3UC pie->Digit[x] = IBuf[Octet+Off] & 0x7f; Off++; x++; -/* }while((IBuf[Octet+Off]&0x80) != 0 && x < 20); Temporary dirty hack. */ - }while(Q931MoreIE()); + }while((IBuf[Octet+Off]&0x80) != 0 && x < 20); Q931IESizeTest(Q931E_CALLINGNUM); diff --git a/libs/openzap/src/isdn/include/Q931.h b/libs/openzap/src/isdn/include/Q931.h index b5251e2d7a..00e4f3738f 100644 --- a/libs/openzap/src/isdn/include/Q931.h +++ b/libs/openzap/src/isdn/include/Q931.h @@ -222,7 +222,7 @@ /* WARNING! Initialize Q931CreateDialectCB[] will NULL when increasing the */ /* Q931MAXDLCT value to avoid Q931Initialize from crashing if one entry is */ /* not used. */ -#define Q931MAXDLCT 2 /* Max dialects included in this */ +#define Q931MAXDLCT 4 /* Max dialects included in this */ /* compile. User and Network count as */ /* one dialect each. */ @@ -1932,6 +1932,7 @@ typedef enum /* Network/User Mode. */ typedef enum /* Dialect enum */ { Q931_Dialect_Q931 = 0, + Q931_Dialect_National = 1, Q931_Dialect_Count } Q931Dialect_t; diff --git a/libs/openzap/src/isdn/nationalStateNT.c b/libs/openzap/src/isdn/nationalStateNT.c new file mode 100644 index 0000000000..c18e185b5a --- /dev/null +++ b/libs/openzap/src/isdn/nationalStateNT.c @@ -0,0 +1,126 @@ +/***************************************************************************** + + FileName: nationalStateNT.c + + Contents: National ISDN State Engine for NT (Network Mode). + + The controlling state engine for Q.931 is the state engine + on the NT side. The state engine on the TE side is a slave + of this. The TE side maintain it's own states as described in + ITU-T Q931, but will in raise conditions be overridden by + the NT side. + + License/Copyright: + + Copyright (c) 2007, Jan Vidar Berger, Case Labs, Ltd. All rights reserved. + email:janvb@caselaboratories.com + + Copyright (c) 2007, Michael Jerris. All rights reserved. + email:mike@jerris.com + + Redistribution and use in source and binary forms, with or without + modification, are permitted provided that the following conditions are + met: + + * Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. + * Redistributions in binary form must reproduce the above copyright notice, + this list of conditions and the following disclaimer in the documentation + and/or other materials provided with the distribution. + * Neither the name of the Case Labs, Ltd nor the names of its contributors + may be used to endorse or promote products derived from this software + without specific prior written permission. + + THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE + LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + POSSIBILITY OF SUCH DAMAGE. +*****************************************************************************/ + +#include "national.h" + +/***************************************************************************** + Function: nationalCreateNT + + Description: Will create the National ISDN NT as a Dialect in the stack. The first + bulk set up the message handlers, the second bulk the IE + encoders/coders, and the last bulk set up the state table. + + Parameters: i Dialect index +*****************************************************************************/ +void nationalCreateNT(L3UCHAR i) +{ + Q931SetMesProc(Q931mes_ALERTING, i,Q931ProcAlertingNT, Q931Umes_Alerting, Q931Pmes_Alerting); + Q931SetMesProc(Q931mes_CALL_PROCEEDING, i,Q931ProcCallProceedingNT, Q931Umes_CallProceeding, Q931Pmes_CallProceeding); + Q931SetMesProc(Q931mes_CONNECT, i,Q931ProcConnectNT, Q931Umes_Connect, Q931Pmes_Connect); + Q931SetMesProc(Q931mes_CONNECT_ACKNOWLEDGE, i,Q931ProcConnectAckNT, Q931Umes_ConnectAck, Q931Pmes_ConnectAck); + Q931SetMesProc(Q931mes_PROGRESS, i,Q931ProcProgressNT, Q931Umes_Progress, Q931Pmes_Progress); + Q931SetMesProc(Q931mes_SETUP, i,Q931ProcSetupNT, nationalUmes_Setup, nationalPmes_Setup); + Q931SetMesProc(Q931mes_SETUP_ACKNOWLEDGE, i,Q931ProcSetupAckNT, Q931Umes_SetupAck, Q931Pmes_SetupAck); + Q931SetMesProc(Q931mes_RESUME, i,Q931ProcResumeNT, Q931Umes_Resume, Q931Pmes_Resume); + Q931SetMesProc(Q931mes_RESUME_ACKNOWLEDGE, i,Q931ProcResumeAckNT, Q931Umes_ResumeAck, Q931Pmes_ResumeAck); + Q931SetMesProc(Q931mes_RESUME_REJECT, i,Q931ProcResumeRejectNT, Q931Umes_ResumeReject, Q931Pmes_ResumeReject); + Q931SetMesProc(Q931mes_SUSPEND, i,Q931ProcSuspendNT, Q931Umes_Suspend, Q931Pmes_Suspend); + Q931SetMesProc(Q931mes_SUSPEND_ACKNOWLEDGE, i,Q931ProcSuspendAckNT, Q931Umes_SuspendAck, Q931Pmes_SuspendAck); + Q931SetMesProc(Q931mes_SUSPEND_REJECT, i,Q931ProcSuspendRejectNT, Q931Umes_SuspendReject, Q931Pmes_SuspendReject); + Q931SetMesProc(Q931mes_USER_INFORMATION, i,Q931ProcUserInformationNT, Q931Umes_UserInformation, Q931Pmes_UserInformation); + Q931SetMesProc(Q931mes_DISCONNECT, i,Q931ProcDisconnectNT, Q931Umes_Disconnect, Q931Pmes_Disconnect); + Q931SetMesProc(Q931mes_RELEASE, i,Q931ProcReleaseNT, Q931Umes_Release, Q931Pmes_Release); + Q931SetMesProc(Q931mes_RELEASE_COMPLETE, i,Q931ProcReleaseCompleteNT, Q931Umes_ReleaseComplete, Q931Pmes_ReleaseComplete); + Q931SetMesProc(Q931mes_RESTART, i,Q931ProcRestartNT, Q931Umes_Restart, Q931Pmes_Restart); + Q931SetMesProc(Q931mes_RESTART_ACKNOWLEDGE, i,Q931ProcRestartAckNT, Q931Umes_RestartAck, Q931Pmes_RestartAck); + Q931SetMesProc(Q931mes_CONGESTION_CONTROL, i,Q931ProcCongestionControlNT, Q931Umes_CongestionControl, Q931Pmes_CongestionControl); + Q931SetMesProc(Q931mes_INFORMATION, i,Q931ProcInformationNT, Q931Umes_Information, Q931Pmes_Information); + Q931SetMesProc(Q931mes_NOTIFY, i,Q931ProcNotifyNT, Q931Umes_Notify, Q931Pmes_Notify); + Q931SetMesProc(Q931mes_STATUS, i,Q931ProcStatusNT, Q931Umes_Status, Q931Pmes_Status); + Q931SetMesProc(Q931mes_STATUS_ENQUIRY, i,Q931ProcStatusEnquiryNT, Q931Umes_StatusEnquiry, Q931Pmes_StatusEnquiry); + Q931SetMesProc(Q931mes_SEGMENT, i,Q931ProcSegmentNT, Q931Umes_Segment, Q931Pmes_Segment); + + Q931SetMesProc(Q932mes_FACILITY, i,Q932ProcFacilityNT, Q932Umes_Facility, Q932Pmes_Facility); + Q931SetMesProc(Q932mes_HOLD, i,Q932ProcHoldNT, Q932Umes_Hold, Q932Pmes_Hold); + Q931SetMesProc(Q932mes_HOLD_ACKNOWLEDGE, i,Q932ProcHoldAckNT, Q932Umes_HoldAck, Q932Pmes_HoldAck); + Q931SetMesProc(Q932mes_HOLD_REJECT, i,Q932ProcHoldRejectNT, Q932Umes_HoldReject, Q932Pmes_HoldReject); + Q931SetMesProc(Q932mes_REGISTER, i,Q932ProcRegisterNT, Q932Umes_Register, Q932Pmes_Register); + Q931SetMesProc(Q932mes_RETRIEVE, i,Q932ProcRetrieveNT, Q932Umes_Retrieve, Q932Pmes_Retrieve); + Q931SetMesProc(Q932mes_RETRIEVE_ACKNOWLEDGE,i,Q932ProcRetrieveAckNT, Q932Umes_RetrieveAck, Q932Pmes_RetrieveAck); + Q931SetMesProc(Q932mes_RETRIEVE_REJECT, i,Q932ProcRetrieveRejectNT, Q932Umes_RetrieveReject, Q932Pmes_RetrieveReject); + + /* Set up the IE encoder/decoder handle table.*/ + Q931SetIEProc(Q931ie_SEGMENTED_MESSAGE, i,Q931Pie_Segment, Q931Uie_Segment); + Q931SetIEProc(Q931ie_BEARER_CAPABILITY, i,Q931Pie_BearerCap, Q931Uie_BearerCap); + Q931SetIEProc(Q931ie_CAUSE, i,Q931Pie_Cause, Q931Uie_Cause); + Q931SetIEProc(Q931ie_CALL_IDENTITY, i,Q931Pie_CallID, Q931Uie_CallID); + Q931SetIEProc(Q931ie_CALL_STATE, i,Q931Pie_CallState, Q931Uie_CallState); + Q931SetIEProc(Q931ie_CHANNEL_IDENTIFICATION, i,Q931Pie_ChanID, Q931Uie_ChanID); + Q931SetIEProc(Q931ie_PROGRESS_INDICATOR, i,Q931Pie_ProgInd, Q931Uie_ProgInd); + Q931SetIEProc(Q931ie_NETWORK_SPECIFIC_FACILITIES, i,Q931Pie_NetFac, Q931Uie_NetFac); + Q931SetIEProc(Q931ie_NOTIFICATION_INDICATOR, i,Q931Pie_NotifInd, Q931Uie_NotifInd); + Q931SetIEProc(Q931ie_DISPLAY, i,Q931Pie_Display, Q931Uie_Display); + Q931SetIEProc(Q931ie_DATETIME, i,Q931Pie_DateTime, Q931Uie_DateTime); + Q931SetIEProc(Q931ie_KEYPAD_FACILITY, i,Q931Pie_KeypadFac, Q931Uie_KeypadFac); + Q931SetIEProc(Q931ie_SIGNAL, i,Q931Pie_Signal, Q931Uie_Signal); + Q931SetIEProc(Q931ie_TRANSIT_DELAY_SELECTION_AND_IND, i,Q931Pie_TransNetSel, Q931Uie_TransNetSel); + Q931SetIEProc(Q931ie_CALLING_PARTY_NUMBER, i,nationalPie_CallingNum, nationalUie_CallingNum); + Q931SetIEProc(Q931ie_CALLING_PARTY_SUBADDRESS, i,Q931Pie_CallingSub, Q931Uie_CallingSub); + Q931SetIEProc(Q931ie_CALLED_PARTY_NUMBER, i,Q931Pie_CalledNum, Q931Uie_CalledNum); + Q931SetIEProc(Q931ie_CALLED_PARTY_SUBADDRESS, i,Q931Pie_CalledSub, Q931Uie_CalledSub); + Q931SetIEProc(Q931ie_TRANSIT_NETWORK_SELECTION, i,Q931Pie_TransNetSel, Q931Uie_TransNetSel); + Q931SetIEProc(Q931ie_RESTART_INDICATOR, i,Q931Pie_RestartInd, Q931Uie_RestartInd); + Q931SetIEProc(Q931ie_LOW_LAYER_COMPATIBILITY, i,Q931Pie_LLComp, Q931Uie_LLComp); + Q931SetIEProc(Q931ie_HIGH_LAYER_COMPATIBILITY, i,Q931Pie_HLComp, Q931Uie_HLComp); + Q931SetIEProc(Q931ie_USER_USER, i,Q931Pie_UserUser, Q931Uie_UserUser); + Q931SetIEProc(nationalie_GENERIC_DIGITS, i,nationalPie_GenericDigits, nationalUie_GenericDigits); + + /* The following define a state machine. The point is that the Message */ + /* procs can when search this to find out if the message/state */ + /* combination is legale. If not, the proc for unexpected message apply.*/ + + /* TODO define state table here */ +} diff --git a/libs/openzap/src/isdn/nationalStateTE.c b/libs/openzap/src/isdn/nationalStateTE.c new file mode 100644 index 0000000000..f8b8a9f90c --- /dev/null +++ b/libs/openzap/src/isdn/nationalStateTE.c @@ -0,0 +1,210 @@ +/***************************************************************************** + + FileName: nationalStateTE.c + + Contents: National ISDN State Engine for TE (User Mode). + + The controlling state engine for Q.931 is the state engine + on the NT side. The state engine on the TE side is a slave + of this. The TE side maintain it's own states as described in + ITU-T Q931, but will in raise conditions be overridden by + the NT side. + + This reference implementation uses a process per message, + meaning that each message must check call states. This + is easier for dialect maintenance as each message proc + can be replaced individually. A new TE variant only + need to copy the Q931CreateTE and replace those procs or + need to override. + + License/Copyright: + + Copyright (c) 2007, Jan Vidar Berger, Case Labs, Ltd. All rights reserved. + email:janvb@caselaboratories.com + + Copyright (c) 2007, Michael Jerris. All rights reserved. + email:mike@jerris.com + + Redistribution and use in source and binary forms, with or without + modification, are permitted provided that the following conditions are + met: + + * Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. + * Redistributions in binary form must reproduce the above copyright notice, + this list of conditions and the following disclaimer in the documentation + and/or other materials provided with the distribution. + * Neither the name of the Case Labs, Ltd nor the names of its contributors + may be used to endorse or promote products derived from this software + without specific prior written permission. + + THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE + LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + POSSIBILITY OF SUCH DAMAGE. +*****************************************************************************/ + +#include "national.h" + +/***************************************************************************** + Function: nationalCreateTE + + Description: Will create the National TE as a Dialect in the stack. The first + bulk set up the message handlers, the second bulk the IE + encoders/coders, and the last bulk set up the state table. + + Parameters: i Dialect index +*****************************************************************************/ +void nationalCreateTE(L3UCHAR i) +{ + Q931SetMesProc(Q931mes_ALERTING, i,Q931ProcAlertingTE, Q931Umes_Alerting, Q931Pmes_Alerting); + Q931SetMesProc(Q931mes_CALL_PROCEEDING, i,Q931ProcCallProceedingTE, Q931Umes_CallProceeding, Q931Pmes_CallProceeding); + Q931SetMesProc(Q931mes_CONNECT, i,Q931ProcConnectTE, Q931Umes_Connect, Q931Pmes_Connect); + Q931SetMesProc(Q931mes_CONNECT_ACKNOWLEDGE, i,Q931ProcConnectAckTE, Q931Umes_ConnectAck, Q931Pmes_ConnectAck); + Q931SetMesProc(Q931mes_PROGRESS, i,Q931ProcProgressTE, Q931Umes_Progress, Q931Pmes_Progress); + Q931SetMesProc(Q931mes_SETUP, i,Q931ProcSetupTE, nationalUmes_Setup, nationalPmes_Setup); + Q931SetMesProc(Q931mes_SETUP_ACKNOWLEDGE, i,Q931ProcSetupAckTE, Q931Umes_SetupAck, Q931Pmes_SetupAck); + Q931SetMesProc(Q931mes_RESUME, i,Q931ProcResumeTE, Q931Umes_Resume, Q931Pmes_Resume); + Q931SetMesProc(Q931mes_RESUME_ACKNOWLEDGE, i,Q931ProcResumeAckTE, Q931Umes_ResumeAck, Q931Pmes_ResumeAck); + Q931SetMesProc(Q931mes_RESUME_REJECT, i,Q931ProcResumeRejectTE, Q931Umes_ResumeReject, Q931Pmes_ResumeReject); + Q931SetMesProc(Q931mes_SUSPEND, i,Q931ProcSuspendTE, Q931Umes_Suspend, Q931Pmes_Suspend); + Q931SetMesProc(Q931mes_SUSPEND_ACKNOWLEDGE, i,Q931ProcSuspendAckTE, Q931Umes_SuspendAck, Q931Pmes_SuspendAck); + Q931SetMesProc(Q931mes_SUSPEND_REJECT, i,Q931ProcSuspendRejectTE, Q931Umes_SuspendReject, Q931Pmes_SuspendReject); + Q931SetMesProc(Q931mes_USER_INFORMATION, i,Q931ProcUserInformationTE, Q931Umes_UserInformation, Q931Pmes_UserInformation); + Q931SetMesProc(Q931mes_DISCONNECT, i,Q931ProcDisconnectTE, Q931Umes_Disconnect, Q931Pmes_Disconnect); + Q931SetMesProc(Q931mes_RELEASE, i,Q931ProcReleaseTE, Q931Umes_Release, Q931Pmes_Release); + Q931SetMesProc(Q931mes_RELEASE_COMPLETE, i,Q931ProcReleaseCompleteTE, Q931Umes_ReleaseComplete, Q931Pmes_ReleaseComplete); + Q931SetMesProc(Q931mes_RESTART, i,Q931ProcRestartTE, Q931Umes_Restart, Q931Pmes_Restart); + Q931SetMesProc(Q931mes_RESTART_ACKNOWLEDGE, i,Q931ProcRestartAckTE, Q931Umes_RestartAck, Q931Pmes_RestartAck); + Q931SetMesProc(Q931mes_CONGESTION_CONTROL, i,Q931ProcCongestionControlTE, Q931Umes_CongestionControl, Q931Pmes_CongestionControl); + Q931SetMesProc(Q931mes_INFORMATION, i,Q931ProcInformationTE, Q931Umes_Information, Q931Pmes_Information); + Q931SetMesProc(Q931mes_NOTIFY, i,Q931ProcNotifyTE, Q931Umes_Notify, Q931Pmes_Notify); + Q931SetMesProc(Q931mes_STATUS, i,Q931ProcStatusTE, Q931Umes_Status, Q931Pmes_Status); + Q931SetMesProc(Q931mes_STATUS_ENQUIRY, i,Q931ProcStatusEnquiryTE, Q931Umes_StatusEnquiry, Q931Pmes_StatusEnquiry); + Q931SetMesProc(Q931mes_SEGMENT, i,Q931ProcSegmentTE, Q931Umes_Segment, Q931Pmes_Segment); + + Q931SetMesProc(Q932mes_FACILITY, i,Q932ProcFacilityTE, Q932Umes_Facility, Q932Pmes_Facility); + Q931SetMesProc(Q932mes_HOLD, i,Q932ProcHoldTE, Q932Umes_Hold, Q932Pmes_Hold); + Q931SetMesProc(Q932mes_HOLD_ACKNOWLEDGE, i,Q932ProcHoldAckTE, Q932Umes_HoldAck, Q932Pmes_HoldAck); + Q931SetMesProc(Q932mes_HOLD_REJECT, i,Q932ProcHoldRejectTE, Q932Umes_HoldReject, Q932Pmes_HoldReject); + Q931SetMesProc(Q932mes_REGISTER, i,Q932ProcRegisterTE, Q932Umes_Register, Q932Pmes_Register); + Q931SetMesProc(Q932mes_RETRIEVE, i,Q932ProcRetrieveTE, Q932Umes_Retrieve, Q932Pmes_Retrieve); + Q931SetMesProc(Q932mes_RETRIEVE_ACKNOWLEDGE,i,Q932ProcRetrieveAckTE, Q932Umes_RetrieveAck, Q932Pmes_RetrieveAck); + Q931SetMesProc(Q932mes_RETRIEVE_REJECT, i,Q932ProcRetrieveRejectTE, Q932Umes_RetrieveReject, Q932Pmes_RetrieveReject); + + /* Set up the IE encoder/decoder handle table.*/ + Q931SetIEProc(Q931ie_SEGMENTED_MESSAGE, i,Q931Pie_Segment, Q931Uie_Segment); + Q931SetIEProc(Q931ie_BEARER_CAPABILITY, i,Q931Pie_BearerCap, Q931Uie_BearerCap); + Q931SetIEProc(Q931ie_CAUSE, i,Q931Pie_Cause, Q931Uie_Cause); + Q931SetIEProc(Q931ie_CALL_IDENTITY, i,Q931Pie_CallID, Q931Uie_CallID); + Q931SetIEProc(Q931ie_CALL_STATE, i,Q931Pie_CallState, Q931Uie_CallState); + Q931SetIEProc(Q931ie_CHANNEL_IDENTIFICATION, i,Q931Pie_ChanID, Q931Uie_ChanID); + Q931SetIEProc(Q931ie_PROGRESS_INDICATOR, i,Q931Pie_ProgInd, Q931Uie_ProgInd); + Q931SetIEProc(Q931ie_NETWORK_SPECIFIC_FACILITIES, i,Q931Pie_NetFac, Q931Uie_NetFac); + Q931SetIEProc(Q931ie_NOTIFICATION_INDICATOR, i,Q931Pie_NotifInd, Q931Uie_NotifInd); + Q931SetIEProc(Q931ie_DISPLAY, i,Q931Pie_Display, Q931Uie_Display); + Q931SetIEProc(Q931ie_DATETIME, i,Q931Pie_DateTime, Q931Uie_DateTime); + Q931SetIEProc(Q931ie_KEYPAD_FACILITY, i,Q931Pie_KeypadFac, Q931Uie_KeypadFac); + Q931SetIEProc(Q931ie_SIGNAL, i,Q931Pie_Signal, Q931Uie_Signal); + Q931SetIEProc(Q931ie_TRANSIT_DELAY_SELECTION_AND_IND, i,Q931Pie_TransNetSel, Q931Uie_TransNetSel); + Q931SetIEProc(Q931ie_CALLING_PARTY_NUMBER, i,nationalPie_CallingNum, nationalUie_CallingNum); + Q931SetIEProc(Q931ie_CALLING_PARTY_SUBADDRESS, i,Q931Pie_CallingSub, Q931Uie_CallingSub); + Q931SetIEProc(Q931ie_CALLED_PARTY_NUMBER, i,Q931Pie_CalledNum, Q931Uie_CalledNum); + Q931SetIEProc(Q931ie_CALLED_PARTY_SUBADDRESS, i,Q931Pie_CalledSub, Q931Uie_CalledSub); + Q931SetIEProc(Q931ie_TRANSIT_NETWORK_SELECTION, i,Q931Pie_TransNetSel, Q931Uie_TransNetSel); + Q931SetIEProc(Q931ie_RESTART_INDICATOR, i,Q931Pie_RestartInd, Q931Uie_RestartInd); + Q931SetIEProc(Q931ie_LOW_LAYER_COMPATIBILITY, i,Q931Pie_LLComp, Q931Uie_LLComp); + Q931SetIEProc(Q931ie_HIGH_LAYER_COMPATIBILITY, i,Q931Pie_HLComp, Q931Uie_HLComp); + Q931SetIEProc(Q931ie_USER_USER, i,Q931Pie_UserUser, Q931Uie_UserUser); + Q931SetIEProc(nationalie_GENERIC_DIGITS, i,nationalPie_GenericDigits, nationalUie_GenericDigits); + + /* The following define a state machine. The point is that the Message */ + /* procs can when search this to find out if the message/state */ + /* combination is legale. If not, the proc for unexpected message apply.*/ + + /* State 0 Idle */ + Q931AddStateEntry(i,Q931_U0, Q931mes_RESUME, 2); + Q931AddStateEntry(i,Q931_U0, Q931mes_SETUP, 4); + Q931AddStateEntry(i,Q931_U0, Q931mes_SETUP, 2); + Q931AddStateEntry(i,Q931_U0, Q931mes_STATUS, 4); + Q931AddStateEntry(i,Q931_U0, Q931mes_RELEASE, 4); + Q931AddStateEntry(i,Q931_U0, Q931mes_RELEASE_COMPLETE,4); + + /* State 1 Call Initiating */ + Q931AddStateEntry(i,Q931_U1, Q931mes_DISCONNECT, 2); + Q931AddStateEntry(i,Q931_U1, Q931mes_SETUP_ACKNOWLEDGE, 4); + Q931AddStateEntry(i,Q931_U1, Q931mes_RELEASE_COMPLETE,4); + Q931AddStateEntry(i,Q931_U1, Q931mes_CALL_PROCEEDING, 4); + Q931AddStateEntry(i,Q931_U1, Q931mes_ALERTING, 4); + Q931AddStateEntry(i,Q931_U1, Q931mes_CONNECT, 4); + + /* State 2 Overlap Sending */ + Q931AddStateEntry(i,Q931_U2, Q931mes_INFORMATION, 2); + Q931AddStateEntry(i,Q931_U2, Q931mes_CALL_PROCEEDING, 4); + Q931AddStateEntry(i,Q931_U2, Q931mes_ALERTING, 4); + Q931AddStateEntry(i,Q931_U2, Q931mes_PROGRESS, 4); + Q931AddStateEntry(i,Q931_U2, Q931mes_CONNECT, 4); + Q931AddStateEntry(i,Q931_U2, Q931mes_RELEASE, 2); + + /* State 3 Outgoing Call Proceeding */ + Q931AddStateEntry(i,Q931_U3, Q931mes_PROGRESS, 4); + Q931AddStateEntry(i,Q931_U3, Q931mes_ALERTING, 4); + Q931AddStateEntry(i,Q931_U3, Q931mes_CONNECT, 4); + Q931AddStateEntry(i,Q931_U3, Q931mes_RELEASE, 2); + + /* State 4 Call Delivered */ + Q931AddStateEntry(i,Q931_U4, Q931mes_CONNECT, 4); + + /* State 6 Call Precent */ + Q931AddStateEntry(i,Q931_U6, Q931mes_INFORMATION, 2); + Q931AddStateEntry(i,Q931_U6, Q931mes_ALERTING, 2); + Q931AddStateEntry(i,Q931_U6, Q931mes_CALL_PROCEEDING,2); + Q931AddStateEntry(i,Q931_U6, Q931mes_CONNECT, 2); + Q931AddStateEntry(i,Q931_U6, Q931mes_RELEASE_COMPLETE,2); + Q931AddStateEntry(i,Q931_U6, Q931mes_RELEASE, 4); + Q931AddStateEntry(i,Q931_U6, Q931mes_DISCONNECT, 4); + + /* State 7 Call Received */ + Q931AddStateEntry(i,Q931_U7, Q931mes_CONNECT, 2); + + /* State 8 Connect request */ + Q931AddStateEntry(i,Q931_U8, Q931mes_CONNECT_ACKNOWLEDGE, 4); + + /* State 9 Incoming Call Proceeding */ + Q931AddStateEntry(i,Q931_U9, Q931mes_CONNECT, 2); + Q931AddStateEntry(i,Q931_U9, Q931mes_ALERTING, 2); + Q931AddStateEntry(i,Q931_U9, Q931mes_PROGRESS, 2); + + /* State 10 Active */ + Q931AddStateEntry(i,Q931_U10, Q931mes_SUSPEND, 2); + Q931AddStateEntry(i,Q931_U10, Q931mes_NOTIFY, 4); + Q931AddStateEntry(i,Q931_U10, Q931mes_NOTIFY, 2); + + /* State 11 Disconnect Request */ + Q931AddStateEntry(i,Q931_U11, Q931mes_RELEASE, 4); + Q931AddStateEntry(i,Q931_U11, Q931mes_DISCONNECT, 4); + Q931AddStateEntry(i,Q931_U11, Q931mes_NOTIFY, 4); + + /* State 12 Disconnect Ind */ + Q931AddStateEntry(i,Q931_U12, Q931mes_RELEASE, 4); + Q931AddStateEntry(i,Q931_U12, Q931mes_RELEASE, 2); + + /* State 15 Suspend Request */ + Q931AddStateEntry(i,Q931_U15, Q931mes_SUSPEND_ACKNOWLEDGE, 4); + Q931AddStateEntry(i,Q931_U15, Q931mes_SUSPEND_REJECT, 4); + Q931AddStateEntry(i,Q931_U15, Q931mes_DISCONNECT, 4); + Q931AddStateEntry(i,Q931_U15, Q931mes_RELEASE, 4); + +/* TODO + Q931AddStateEntry(i,Q931_U17, + Q931AddStateEntry(i,Q931_U19, + Q931AddStateEntry(i,Q931_U25, +*/ +} diff --git a/libs/openzap/src/isdn/nationalie.c b/libs/openzap/src/isdn/nationalie.c new file mode 100644 index 0000000000..b6e2446350 --- /dev/null +++ b/libs/openzap/src/isdn/nationalie.c @@ -0,0 +1,254 @@ +/***************************************************************************** + + FileName: nationalie.c + + Contents: Information Element Pack/Unpack functions. + + These functions will pack out a National ISDN message from the bit + packed original format into structs that are easier to process + and pack the same structs back into bit fields when sending + messages out. + + The messages contains a short for each possible IE. The MSB + bit flags the precense of an IE, while the remaining bits + are the offset into a buffer to find the actual IE. + + Each IE are supported by 3 functions: + + nationalPie_XXX Pack struct into Q.931 IE + nationalUie_XXX Unpack Q.931 IE into struct + nationalInitIEXXX Initialize IE (see nationalapi.c). + + License/Copyright: + + Copyright (c) 2007, Jan Vidar Berger, Case Labs, Ltd. All rights reserved. + email:janvb@caselaboratories.com + + Copyright (c) 2007, Michael Jerris. All rights reserved. + email:mike@jerris.com + + Redistribution and use in source and binary forms, with or without + modification, are permitted provided that the following conditions are + met: + + * Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. + * Redistributions in binary form must reproduce the above copyright notice, + this list of conditions and the following disclaimer in the documentation + and/or other materials provided with the distribution. + * Neither the name of the Case Labs, Ltd nor the names of its contributors + may be used to endorse or promote products derived from this software + without specific prior written permission. + + THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE + LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + POSSIBILITY OF SUCH DAMAGE. +*****************************************************************************/ + +#include "national.h" + +/***************************************************************************** + + Macro: Q931MoreIE + + Description: Local helper macro detecting if there is more IE space left + based on the 3 standard parameters Octet, Off and IESpace. + This can be used to test if the IE is completed to avoid + that the header of the next IE is interpreted as a part of + the current IE. + +*****************************************************************************/ +#define Q931MoreIE() (Octet+Off - 2 < IESize) + +#define Q931IESizeTest(x) {\ + if(Octet+Off-2 != IESize)\ + {\ + Q931SetError(pTrunk,x, Octet, Off);\ + return x;\ + }\ + } + +/***************************************************************************** + + Function: nationalUie_GenericDigits + + Parameters: pIE[OUT] ptr to Information Element id. + IBuf[IN] ptr to a packed ie. + OBuf[OUT] ptr to buffer for Unpacked ie. + IOff[IN\OUT] Input buffer offset + OOff[IN\OUT] Output buffer offset + + + Ibuf and OBuf points directly to buffers. The IOff and OOff + must be updated, but are otherwise not used in the ie unpack. + + Return Value: Error Message + +*****************************************************************************/ +L3INT nationalUie_GenericDigits(Q931_TrunkInfo_t *pTrunk, ie *pIE, L3UCHAR * IBuf, L3UCHAR * OBuf, L3INT *IOff, L3INT *OOff) +{ + nationalie_GenericDigits * pie = (nationalie_GenericDigits*)OBuf; + L3INT Off = 0; + L3INT Octet = 0; + L3INT x=0; + L3INT IESize; + + *pIE=0; + + /* Octet 1 */ + pie->IEId = IBuf[Octet++]; + + /* Octet 2 */ + IESize = IBuf[Octet++]; + + Q931SetIE(*pIE, *OOff); + + *IOff = (*IOff) + Octet + Off; + *OOff = (*OOff) + sizeof(nationalie_GenericDigits) + x -1; + + pie->Size = (L3UCHAR)(sizeof(nationalie_GenericDigits) + x -1); + + return Q931E_NO_ERROR; +} + +/***************************************************************************** + + Function: nationalPie_GenericDigits + + Parameters: IBuf[IN] Ptr to struct. + OBuf[OUT] Ptr tp packed output buffer. + Octet[IN/OUT] Offset into OBuf. + + Return Value: Error code, 0 = OK + +*****************************************************************************/ + +L3INT nationalPie_GenericDigits(Q931_TrunkInfo_t *pTrunk, L3UCHAR *IBuf, L3UCHAR *OBuf, L3INT *Octet) +{ + OBuf[(*Octet)++] = nationalie_GENERIC_DIGITS ; + OBuf[(*Octet)++] = 2; + + return Q931E_NO_ERROR; +} + +/***************************************************************************** + + Function: nationalUie_CallingNum + + Parameters: pIE[OUT] ptr to Information Element id. + IBuf[IN] ptr to a packed ie. + OBuf[OUT] ptr to buffer for Unpacked ie. + IOff[IN\OUT] Input buffer offset + OOff[IN\OUT] Output buffer offset + + Ibuf and OBuf points directly to buffers. The IOff and OOff + must be updated, but are otherwise not used in the ie unpack. + + Return Value: Error Message + +*****************************************************************************/ +L3INT nationalUie_CallingNum(Q931_TrunkInfo_t *pTrunk, ie *pIE, L3UCHAR * IBuf, L3UCHAR * OBuf, L3INT *IOff, L3INT *OOff) +{ + Q931ie_CallingNum * pie = (Q931ie_CallingNum*)OBuf; + L3INT Off = 0; + L3INT Octet = 0; + L3INT x; + L3INT IESize; + + *pIE=0; + + /* Octet 1 */ + pie->IEId = IBuf[Octet]; + Octet ++; + + /* Octet 2 */ + IESize = IBuf[Octet ++]; + + /* Octet 3 */ + pie->TypNum = (IBuf[Octet+Off] >> 4) & 0x07; + pie->NumPlanID = IBuf[Octet+Off] & 0x0f; + + /* Octet 3a */ + if((IBuf[Octet+Off] & 0x80) != 0) + { + Off++; + pie->PresInd = (IBuf[Octet+Off] >> 5) & 0x03; + pie->ScreenInd = IBuf[Octet+Off] & 0x03; + } + Octet++; + + /* Octet 4a*/ + x=0; + do{ + pie->Digit[x] = IBuf[Octet+Off] & 0x7f; + Off++; + x++; + }while(Q931MoreIE()); + + Q931IESizeTest(Q931E_CALLINGNUM); + + Q931SetIE(*pIE, *OOff); + + *IOff = (*IOff) + Octet + Off; + *OOff = (*OOff) + sizeof(Q931ie_CallingNum) + x - 1; + pie->Size = (L3UCHAR)(sizeof(Q931ie_CallingNum) + x - 1); + + return Q931E_NO_ERROR; +} + +/***************************************************************************** + + Function: nationalPie_CallingNum + + Parameters: IBuf[IN] Ptr to struct. + OBuf[OUT] Ptr tp packed output buffer. + Octet[IN/OUT] Offset into OBuf. + + Return Value: Error code, 0 = OK + +*****************************************************************************/ +L3INT nationalPie_CallingNum(Q931_TrunkInfo_t *pTrunk, L3UCHAR *IBuf, L3UCHAR *OBuf, L3INT *Octet) +{ + Q931ie_CallingSub * pIE = (Q931ie_CallingSub*)IBuf; + L3INT rc=0; + L3INT Beg=*Octet; + L3INT li; + L3INT sN = pIE->Size - sizeof(Q931ie_CalledSub) + 1; + L3INT x; + + /* Octet 1 */ + OBuf[(*Octet)++] = Q931ie_CALLING_PARTY_SUBADDRESS; + li=(*Octet)++; + + /* Octet 3 */ + OBuf[(*Octet)++] = 0x80 | (pIE->TypNum << 4) | (pIE->OddEvenInd << 3); + + /* Octet 3a */ + /* + + Details about the use and how to detect if Octet 3a is used + are very weak. Temp left out. + + Octet 3 msb is set to 1 to indicate that this is not present + + */ + + /* Octet 4 */ + for(x=0;xDigit[x]; + } + + OBuf[(*Octet)-1] |= 0x80; /* Terminate bit */ + + OBuf[li] = (L3UCHAR)((*Octet)-Beg) - 2; + return rc; +} diff --git a/libs/openzap/src/isdn/nationalmes.c b/libs/openzap/src/isdn/nationalmes.c new file mode 100644 index 0000000000..c32398d00d --- /dev/null +++ b/libs/openzap/src/isdn/nationalmes.c @@ -0,0 +1,301 @@ +/***************************************************************************** + + FileName: nationalmes.c + + Contents: Pack/Unpack functions. These functions will unpack a National ISDN + message from the bit packed original format into structs + that contains variables sized by the user. It will also pack + the struct back into a Q.931 message as required. + + See national.h for description. + + License/Copyright: + + Copyright (c) 2007, Jan Vidar Berger, Case Labs, Ltd. All rights reserved. + email:janvb@caselaboratories.com + + Copyright (c) 2007, Michael Jerris. All rights reserved. + email:mike@jerris.com + + Redistribution and use in source and binary forms, with or without + modification, are permitted provided that the following conditions are + met: + + * Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. + * Redistributions in binary form must reproduce the above copyright notice, + this list of conditions and the following disclaimer in the documentation + and/or other materials provided with the distribution. + * Neither the name of the Case Labs, Ltd nor the names of its contributors + may be used to endorse or promote products derived from this software + without specific prior written permission. + + THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE + LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + POSSIBILITY OF SUCH DAMAGE. + +*****************************************************************************/ + +#include "national.h" + +/***************************************************************************** + + Function: nationalUmes_Setup + +*****************************************************************************/ +L3INT nationalUmes_Setup(Q931_TrunkInfo_t *pTrunk, L3UCHAR *IBuf, L3UCHAR *OBuf, L3INT IOff, L3INT Size) +{ + /* L3INT i = IOff; */ + L3INT ir=0; + L3INT OOff=0; + Q931mes_Setup *mes = (Q931mes_Setup*)OBuf; + L3INT rc=Q931E_NO_ERROR; + while(IOff < Size) + { + switch(IBuf[IOff]) + { + case Q931ie_SENDING_COMPLETE: + rc = Q931Uie[pTrunk->Dialect][IBuf[IOff]](pTrunk, &mes->SendComplete,&IBuf[IOff], &mes->buf[OOff], &IOff, &OOff); + if(rc != Q931E_NO_ERROR) + return rc; + break; + case Q931ie_REPEAT_INDICATOR: + if(ir==0) + { + rc = Q931Uie[pTrunk->Dialect][IBuf[IOff]](pTrunk, &mes->RepeatInd,&IBuf[IOff], &mes->buf[OOff], &IOff, &OOff); + ir++; + } + else if(ir==1) + { + rc = Q931Uie[pTrunk->Dialect][IBuf[IOff]](pTrunk, &mes->LLRepeatInd,&IBuf[IOff], &mes->buf[OOff], &IOff, &OOff); + ir++; + } + else + { + return Q931E_ILLEGAL_IE; + } + break; + case Q931ie_BEARER_CAPABILITY: + rc = Q931Uie[pTrunk->Dialect][IBuf[IOff]](pTrunk, &mes->BearerCap,&IBuf[IOff], &mes->buf[OOff], &IOff, &OOff); + if(rc != Q931E_NO_ERROR) + return rc; + break; + case Q931ie_CHANNEL_IDENTIFICATION: + rc = Q931Uie[pTrunk->Dialect][IBuf[IOff]](pTrunk, &mes->ChanID,&IBuf[IOff], &mes->buf[OOff], &IOff, &OOff); + if(rc != Q931E_NO_ERROR) + return rc; + break; + case Q931ie_PROGRESS_INDICATOR: + rc = Q931Uie[pTrunk->Dialect][IBuf[IOff]](pTrunk, &mes->ProgInd,&IBuf[IOff], &mes->buf[OOff], &IOff, &OOff); + if(rc != Q931E_NO_ERROR) + return rc; + break; + case Q931ie_NETWORK_SPECIFIC_FACILITIES: + rc = Q931Uie[pTrunk->Dialect][IBuf[IOff]](pTrunk, &mes->NetFac,&IBuf[IOff], &mes->buf[OOff], &IOff, &OOff); + if(rc != Q931E_NO_ERROR) + return rc; + break; + case Q931ie_DISPLAY: + rc = Q931Uie[pTrunk->Dialect][IBuf[IOff]](pTrunk, &mes->Display,&IBuf[IOff], &mes->buf[OOff], &IOff, &OOff); + if(rc != Q931E_NO_ERROR) + return rc; + break; + case Q931ie_DATETIME: + rc = Q931Uie[pTrunk->Dialect][IBuf[IOff]](pTrunk, &mes->DateTime,&IBuf[IOff], &mes->buf[OOff], &IOff, &OOff); + if(rc != Q931E_NO_ERROR) + return rc; + break; + case Q931ie_KEYPAD_FACILITY: + rc = Q931Uie[pTrunk->Dialect][IBuf[IOff]](pTrunk, &mes->KeypadFac,&IBuf[IOff], &mes->buf[OOff], &IOff, &OOff); + if(rc != Q931E_NO_ERROR) + return rc; + break; + case Q931ie_SIGNAL: + rc = Q931Uie[pTrunk->Dialect][IBuf[IOff]](pTrunk, &mes->Signal,&IBuf[IOff], &mes->buf[OOff], &IOff, &OOff); + if(rc != Q931E_NO_ERROR) + return rc; + break; + case Q931ie_CALLING_PARTY_NUMBER: + rc = Q931Uie[pTrunk->Dialect][IBuf[IOff]](pTrunk, &mes->CallingNum,&IBuf[IOff], &mes->buf[OOff], &IOff, &OOff); + if(rc != Q931E_NO_ERROR) + return rc; + break; + case Q931ie_CALLING_PARTY_SUBADDRESS: + rc = Q931Uie[pTrunk->Dialect][IBuf[IOff]](pTrunk, &mes->CallingSub,&IBuf[IOff], &mes->buf[OOff], &IOff, &OOff); + if(rc != Q931E_NO_ERROR) + return rc; + break; + case Q931ie_CALLED_PARTY_NUMBER: + rc = Q931Uie[pTrunk->Dialect][IBuf[IOff]](pTrunk, &mes->CalledSub,&IBuf[IOff], &mes->buf[OOff], &IOff, &OOff); + if(rc != Q931E_NO_ERROR) + return rc; + break; + case Q931ie_CALLED_PARTY_SUBADDRESS: + rc = Q931Uie[pTrunk->Dialect][IBuf[IOff]](pTrunk, &mes->CalledSub,&IBuf[IOff], &mes->buf[OOff], &IOff, &OOff); + if(rc != Q931E_NO_ERROR) + return rc; + break; + case Q931ie_TRANSIT_NETWORK_SELECTION: + rc = Q931Uie[pTrunk->Dialect][IBuf[IOff]](pTrunk, &mes->TransNetSel,&IBuf[IOff], &mes->buf[OOff], &IOff, &OOff); + if(rc != Q931E_NO_ERROR) + return rc; + break; + case Q931ie_LOW_LAYER_COMPATIBILITY: + rc = Q931Uie[pTrunk->Dialect][IBuf[IOff]](pTrunk, &mes->LLComp,&IBuf[IOff], &mes->buf[OOff], &IOff, &OOff); + if(rc != Q931E_NO_ERROR) + return rc; + break; + case Q931ie_HIGH_LAYER_COMPATIBILITY: + rc = Q931Uie[pTrunk->Dialect][IBuf[IOff]](pTrunk, &mes->HLComp,&IBuf[IOff], &mes->buf[OOff], &IOff, &OOff); + if(rc != Q931E_NO_ERROR) + return rc; + break; + case nationalie_GENERIC_DIGITS: + /* TODO: Implement this ie */ + break; + default: + return Q931E_ILLEGAL_IE; + break; + } + } + mes->Size = sizeof(Q931mes_Setup) - 1 + OOff; + return Q931E_NO_ERROR; +} + +/***************************************************************************** + + Function: nationalPmes_Setup + + Decription: Pack a Q931mes_Setup into a real Q.931 message. The user will + set up a SETUP message and issue this to the stack where it + is processed by Q931ProcSetup that processes and validates + it before it actually sends it out. This function is called + to compute the real Q.931 message. + + Parameters: IBuf[IN] Ptr to un-packed struct + ISize[IN] Size of input buffer (unpacked message). + OBuf[OUT] Ptr to packed 'octet' wise message. + OSize[OUT] Size of packed message. + + Called By: Q931ProcSetup + +*****************************************************************************/ +L3INT nationalPmes_Setup(Q931_TrunkInfo_t *pTrunk, L3UCHAR *IBuf, L3INT ISize, L3UCHAR *OBuf, L3INT *OSize) +{ + L3INT rc = Q931E_NO_ERROR; + Q931mes_Setup *pMes = (Q931mes_Setup *)IBuf; + L3INT Octet = 0; + + /* Q931 Message Header */ + + OBuf[Octet++] = pMes->ProtDisc; /* Protocol discriminator */ + OBuf[Octet++] = 2; /* length is 2 octets */ + OBuf[Octet++] = (L3UCHAR)(pMes->CRV>>8); /* msb */ + OBuf[Octet++] = (L3UCHAR)(pMes->CRV); /* lsb */ + OBuf[Octet++] = pMes->MesType; /* message header */ + + /* Sending Complete */ + if(Q931IsIEPresent(pMes->SendComplete)) + OBuf[Octet++] = (L3UCHAR)(pMes->SendComplete & 0x00ff); + + /* Repeat Indicator */ + if(Q931IsIEPresent(pMes->RepeatInd)) + OBuf[Octet++] = (L3UCHAR)(pMes->RepeatInd & 0x00ff); + + /* Bearer capability */ + if(Q931IsIEPresent(pMes->BearerCap)) + { + if((rc=Q931Pie[pTrunk->Dialect][Q931ie_BEARER_CAPABILITY](pTrunk, Q931GetIEPtr(pMes->BearerCap,pMes->buf), OBuf, &Octet))!=0) + return rc; + } + else + { + rc=Q931E_BEARERCAP; + } + + /* Channel Identification */ + if(Q931IsIEPresent(pMes->ChanID)) + if((rc=Q931Pie[pTrunk->Dialect][Q931ie_CHANNEL_IDENTIFICATION](pTrunk, Q931GetIEPtr(pMes->ChanID,pMes->buf), OBuf, &Octet))!=0) + return rc; + + /* Progress indicator */ + if(Q931IsIEPresent(pMes->ProgInd)) + if((rc=Q931Pie[pTrunk->Dialect][Q931ie_PROGRESS_INDICATOR](pTrunk, Q931GetIEPtr(pMes->ProgInd,pMes->buf), OBuf, &Octet))!=0) + return rc; + + /* Network spesific facilities */ + if(Q931IsIEPresent(pMes->NetFac)) + if((rc=Q931Pie[pTrunk->Dialect][Q931ie_NETWORK_SPECIFIC_FACILITIES](pTrunk, Q931GetIEPtr(pMes->NetFac,pMes->buf), OBuf, &Octet))!=0) + return rc; + + /* Display */ + if(Q931IsIEPresent(pMes->Display)) + if((rc=Q931Pie[pTrunk->Dialect][Q931ie_DISPLAY](pTrunk, Q931GetIEPtr(pMes->Display,pMes->buf), OBuf, &Octet))!=0) + return rc; + + /* Date/Time */ + if(Q931IsIEPresent(pMes->DateTime)) + if((rc=Q931Pie[pTrunk->Dialect][Q931ie_DATETIME](pTrunk, Q931GetIEPtr(pMes->DateTime,pMes->buf), OBuf, &Octet))!=0) + return rc; + + /* Keypad Facility */ + if(Q931IsIEPresent(pMes->KeypadFac)) + if((rc=Q931Pie[pTrunk->Dialect][Q931ie_KEYPAD_FACILITY](pTrunk, Q931GetIEPtr(pMes->KeypadFac,pMes->buf), OBuf, &Octet))!=0) + return rc; + + /* Signal */ + if(Q931IsIEPresent(pMes->Signal)) + if((rc=Q931Pie[pTrunk->Dialect][Q931ie_SIGNAL](pTrunk, Q931GetIEPtr(pMes->Signal,pMes->buf), OBuf, &Octet))!=0) + return rc; + + /* Calling Party Number */ + if(Q931IsIEPresent(pMes->CallingNum)) + if((rc=Q931Pie[pTrunk->Dialect][Q931ie_CALLING_PARTY_NUMBER](pTrunk, Q931GetIEPtr(pMes->CallingNum,pMes->buf), OBuf, &Octet))!=0) + return rc; + + /* Calling Party Subaddress */ + if(Q931IsIEPresent(pMes->CallingSub)) + if((rc=Q931Pie[pTrunk->Dialect][Q931ie_CALLING_PARTY_SUBADDRESS](pTrunk, Q931GetIEPtr(pMes->CallingSub,pMes->buf), OBuf, &Octet))!=0) + return rc; + + /* Called Party number */ + if(Q931IsIEPresent(pMes->CalledNum)) + if((rc=Q931Pie[pTrunk->Dialect][Q931ie_CALLED_PARTY_NUMBER](pTrunk, Q931GetIEPtr(pMes->CalledNum,pMes->buf), OBuf, &Octet))!=0) + return rc; + + /* Called party subaddress */ + if(Q931IsIEPresent(pMes->CalledSub)) + if((rc=Q931Pie[pTrunk->Dialect][Q931ie_CALLED_PARTY_SUBADDRESS](pTrunk, Q931GetIEPtr(pMes->CalledSub,pMes->buf), OBuf, &Octet))!=0) + return rc; + + /* Transit network selection */ + if(Q931IsIEPresent(pMes->TransNetSel)) + if((rc=Q931Pie[pTrunk->Dialect][Q931ie_TRANSIT_NETWORK_SELECTION](pTrunk, Q931GetIEPtr(pMes->TransNetSel,pMes->buf), OBuf, &Octet))!=0) + return rc; + + /* Repeat Indicator */ + if(Q931IsIEPresent(pMes->LLRepeatInd)) + rc = Q931E_UNKNOWN_IE;/* TODO */ + + /* Low Layer Compatibility */ + if(Q931IsIEPresent(pMes->LLComp)) + if((rc=Q931Pie[pTrunk->Dialect][Q931ie_LOW_LAYER_COMPATIBILITY](pTrunk, Q931GetIEPtr(pMes->LLComp,pMes->buf), OBuf, &Octet))!=0) + return rc; + + /* High Layer Compatibility */ + if(Q931IsIEPresent(pMes->HLComp)) + if((rc=Q931Pie[pTrunk->Dialect][Q931ie_HIGH_LAYER_COMPATIBILITY](pTrunk, Q931GetIEPtr(pMes->HLComp,pMes->buf), OBuf, &Octet))!=0) + return rc; + + *OSize = Octet; + + return rc; +}