LibItsGeoNetworking_Functions.ttcn 113 KB
Newer Older
            
            return (f_computeGnTimestamp() / 1000) mod c_uInt16Max;
        }
tepelmann's avatar
tepelmann committed
         * @desc    Number of messages to be sent
         * @return  Number of messages to be sent
tepelmann's avatar
tepelmann committed
         */
        function f_getMessageCount() return integer {
tepelmann's avatar
tepelmann committed
            return PX_MESSAGE_COUNT;
         * @desc    Gets the IUT GN local address
         * @return  IUT's GN_Address
         * @see     PICS_GN_LOCAL_GN_ADDR
berge's avatar
berge committed
        function f_getIutGnLocalAddress() return GN_Address {
            
            return PICS_GN_LOCAL_GN_ADDR;
         * @desc    Gets the IUT GN local address configuration method
         * @return  GnAddressConfigurationMethod - IUT's GN local address configuration method
         * @see     PICS_GN_LOCAL_ADDR_CONF_METHOD
        function f_getIutGnLocalAddressConfigurationMethod() return GnAddressConfigurationMethod {
            return PICS_GN_LOCAL_ADDR_CONF_METHOD;
        }
        
berge's avatar
berge committed
        /**
         * @desc    Gets the IUT MAc address
         * @return  MacAddress - IUT's MAc Address
         * @see     PICS_IUT_MAC_ADDRESS
         */
        function f_getIutMacAddress() return MacAddress {
tepelmann's avatar
tepelmann committed
            return PICS_IUT_MAC_ADDRESS;
         * @desc    Gets the GeoUnicast forwarding algorithm
         * @return  IUT's GeoUnicast forwarding algorithm
         * @see     PICS_GN_GEOUNICAST_FORWARDING_ALGORITHM
         */
        function f_getGeoUnicastForwardingAlgorithm() return GeoUnicastForwardingAlgorithm {
            return PICS_GN_GEOUNICAST_FORWARDING_ALGORITHM;
        }
        
        /**
         * @desc    Gets the GeoBroadcast forwarding algorithm
         * @return  IUT's GeoBroadcast forwarding algorithm
         * @see     PICS_GN_GEOBROADCAST_FORWARDING_ALGORITHM
         */
        function f_getGeoBroadcastForwardingAlgorithm() return GeoBroadcastForwardingAlgorithm {
            return PICS_GN_GEOBROADCAST_FORWARDING_ALGORITHM;
        }
        
         * @desc    Gets the IUT default hop limit
         * @return  IUT's default hop limit
         * @see     PICS_GN_DEFAULT_HOP_LIMIT
         */
        function f_getDefaultHopLimit() return UInt8 {
            return PICS_GN_DEFAULT_HOP_LIMIT;
        }
        /**
         * @desc    Is the ITS-S mobile or stationary?
         * @return  Flags indicating whether the ITS-S is mobile or stationary.
         * @see     PICS_GN_IS_MOBILE
         */
        function f_isMobile() return Bit8 {
            if (PICS_GN_IS_MOBILE) {
              return '10000000'B;
            }
            return '00000000'B;
        }
        
         * @desc    Gets the LS retransmission timer.. Valid for NetRepInterval = default (cong. ctrl).
         * @return  LS retransmission timer in seconds
         * @see     PICS_GN_LOCATION_SERVICE_RETRANSMIT_TIMER
        function f_getLsRetransmitTimer() return float {
tepelmann's avatar
tepelmann committed
            var float v_itsGnLocationServiceRetransmitTimer := int2float(PICS_GN_LOCATION_SERVICE_RETRANSMIT_TIMER/1000);
            
            return v_itsGnLocationServiceRetransmitTimer;
        }
        
fischer's avatar
fischer committed
        /**
         * @desc    Gets the LS retransmission timer for NetRepInterval = medium (cong. ctrl).
         * @return  LS retransmission timer (medium) in seconds
         * @see     PX_GN_LOCATION_SERVICE_TIMER_MEDIUM
fischer's avatar
fischer committed
         */
        function f_getLsRetransmitTimerMedium() return float {
berge's avatar
berge committed
            var float v_itsGnLocationServiceRetransmitTimerMedium := int2float(PX_GN_LOCATION_SERVICE_TIMER_MEDIUM/1000);
fischer's avatar
fischer committed
            
tepelmann's avatar
tepelmann committed
            return v_itsGnLocationServiceRetransmitTimerMedium;
fischer's avatar
fischer committed
        }
        
        /**
         * @desc    Gets the LS retransmission timer for NetRepInterval = maximum (cong. ctrl).
         * @return  LS retransmission timer (maximum) in seconds
         * @see     PX_GN_LOCATION_SERVICE_TIMER_MAXIMUM
fischer's avatar
fischer committed
         */
        function f_getLsRetransmitTimerMaximum() return float {
berge's avatar
berge committed
            var float v_itsGnLocationServiceRetransmitTimerMaximum := int2float(PX_GN_LOCATION_SERVICE_TIMER_MAXIMUM/1000);
fischer's avatar
fischer committed
            
tepelmann's avatar
tepelmann committed
            return v_itsGnLocationServiceRetransmitTimerMaximum;
fischer's avatar
fischer committed
        }
fischer's avatar
fischer committed
        /**
         * @desc    Gets the App retransmission timer. Valid for AppRepInterval = default (cong. ctrl).
         * @return  App retransmission timer in seconds
         * @see     PX_GN_APPLICATION_RETRANSMIT_TIMER
fischer's avatar
fischer committed
         */
        function f_getAppRetransmitTimer() return float {
tepelmann's avatar
tepelmann committed
            var float v_itsGnLocationApplicationRetransmitTimer := int2float(PX_GN_APPLICATION_RETRANSMIT_TIMER/1000);
fischer's avatar
fischer committed
            
tepelmann's avatar
tepelmann committed
            return v_itsGnLocationApplicationRetransmitTimer;
fischer's avatar
fischer committed
        }
        
        /**
         * @desc    Gets the App retransmission timer for AppRepInterval = medium (cong. ctrl).
         * @return  App retransmission timer (medium) in seconds
         * @see     PX_GN_APPLICATION_RETRANSMIT_TIMER_MEDIUM
fischer's avatar
fischer committed
         */
        function f_getAppRetransmitTimerMedium() return float {
            var float v_itsGnLocationApplicationRetransmitTimerMedium := int2float(PX_GN_APPLICATION_RETRANSMIT_TIMER_MEDIUM/1000);
fischer's avatar
fischer committed
            
            return v_itsGnLocationApplicationRetransmitTimerMedium;
fischer's avatar
fischer committed
        }
        
        /**
         * @desc    Gets the App retransmission timer for AppRepInterval = maximum (cong. ctrl).
         * @return  App retransmission timer (maximum) in seconds
         * @see     PX_GN_APPLICATION_RETRANSMIT_TIMER_MAXIMUM
fischer's avatar
fischer committed
         */
        function f_getAppRetransmitTimerMaximum() return float {
            var float v_itsGnLocationApplicationRetransmitTimerMaximum := int2float(PX_GN_APPLICATION_RETRANSMIT_TIMER_MAXIMUM/1000);
fischer's avatar
fischer committed
            
            return v_itsGnLocationApplicationRetransmitTimerMaximum;
fischer's avatar
fischer committed
        }
fischer's avatar
fischer committed
        
         * @desc    Gets the LS maximum retransmission number.
         * @return  LS maximum retransmission number
         * @see     PICS_GN_LOCATION_SERVICE_MAX_RETRANS
        function f_getLsMaxRetrans() return integer {
            var integer v_itsGnLocationServiceMaxRetrans := PICS_GN_LOCATION_SERVICE_MAX_RETRANS;
            
            return v_itsGnLocationServiceMaxRetrans;
        }
fischer's avatar
fischer committed
        /**
         * @desc    Gets the Application maximum retransmission number.
         * @return  Application maximum retransmission number
         * @see     PX_GN_APPLICATION_MAX_RETRANS
fischer's avatar
fischer committed
         */
        function f_getAppMaxRetrans() return integer {
            var integer v_itsGnApplicationMaxRetrans := PX_GN_APPLICATION_MAX_RETRANS;
fischer's avatar
fischer committed
            
            return v_itsGnApplicationMaxRetrans;
fischer's avatar
fischer committed
        }
         * @desc    Gets the Location Service packet buffer size.
         * @return  Location Service packet buffer size in Kbytes
         * @see     PICS_GN_LOCATION_SERVICE_PACKET_BUFFER_SIZE
tepelmann's avatar
tepelmann committed
         */
        function f_getLsPacketBufferSize() return integer {
            var integer v_itsGnLocationServicePacketBufferSize := PICS_GN_LOCATION_SERVICE_PACKET_BUFFER_SIZE;
tepelmann's avatar
tepelmann committed
            
            return v_itsGnLocationServicePacketBufferSize;
        } // end f_getLsPacketBufferSize
berge's avatar
berge committed
        /**
         * @desc    Gets the UC forwarding packet buffer size.
         * @return  UC forwarding packet buffer size in bytes
         * @see     PICS_GN_UC_FORWARDING_PACKET_BUFFER_SIZE
tepelmann's avatar
tepelmann committed
         */
berge's avatar
berge committed
        function f_getUcForwardingPacketBufferSize() return integer {
            var integer v_itsGnUcForwardingPacketBufferSize := PICS_GN_UC_FORWARDING_PACKET_BUFFER_SIZE;
            return v_itsGnUcForwardingPacketBufferSize * 1024;
berge's avatar
berge committed
        } // end f_getUcForwardingPacketBufferSize
        
berge's avatar
berge committed
        /**
         * @desc    Gets the BC forwarding packet buffer size.
         * @return  BC forwarding packet buffer size in bytes
         * @see     PICS_GN_BC_FORWARDING_PACKET_BUFFER_SIZE
tepelmann's avatar
tepelmann committed
         */
berge's avatar
berge committed
        function f_getBcForwardingPacketBufferSize() return integer {
            var integer v_itsGnBcForwardingPacketBufferSize := PICS_GN_BC_FORWARDING_PACKET_BUFFER_SIZE;
            return v_itsGnBcForwardingPacketBufferSize * 1024;
tepelmann's avatar
tepelmann committed
        } // end f_getBcForwardingPacketBufferSize
         * @desc    Gets the maximum lifetime of a packet.
         * @return  Maximum lifetime of a packet in seconds
         * @see     PICS_GN_MAX_PACKET_LIFETIME
         */
        function f_getMaxPacketLifeTime() return float {
            var float v_itsGnMaxPacketLifetime := int2float(PICS_GN_MAX_PACKET_LIFETIME);
         * @desc    Gets delta for timers.
         * @return  Delta for timers in seconds
         * @see     PX_T_DELTA
         */
        function f_getDeltaTimer() return float {
tepelmann's avatar
tepelmann committed
            var float v_deltaTimer := PX_T_DELTA;
        /**
         * @desc Gets the beacon service retransmit timer.
tepelmann's avatar
tepelmann committed
         * @return  Beacon service retransmit timer
        function f_getBsRetransmitTimer() return float {
            var float v_itsGnBeaconServiceRetransmitTimer;
            v_itsGnBeaconServiceRetransmitTimer := int2float(
                (PICS_GN_BEACON_SERVICE_RETRANSMIT_TIMER/1000));
         * @desc    Gets the beacon service retransmit timer for NetBeaconInterval = medium (cong. ctrl).
         * @return  Beacon service retransmit timer (medium)
        function f_getBsRetransmitTimerMedium() return float {
tepelmann's avatar
tepelmann committed
            var float v_itsGnBeaconServiceRetransmitTimerMedium; // timer value increased (medium)
tepelmann's avatar
tepelmann committed
            v_itsGnBeaconServiceRetransmitTimerMedium := int2float(
                (PX_GN_BEACON_SERVICE_TIMER_MEDIUM+float2int((f_getBsMaxJitter() - 0.0 +1.0)*rnd()) + 0)/1000);
tepelmann's avatar
tepelmann committed
            return v_itsGnBeaconServiceRetransmitTimerMedium;
         * @desc    Gets the beacon service retransmit timer for NetBeaconInterval = maximum (cong. ctrl).
         * @return  Beacon service retransmit timer (maximum)
        function f_getBsRetransmitTimerMaximum() return float {
tepelmann's avatar
tepelmann committed
            var float v_itsGnBeaconServiceRetransmitTimerMaximum; // timer value increased (maximum)
tepelmann's avatar
tepelmann committed
            v_itsGnBeaconServiceRetransmitTimerMaximum := int2float(
                (PX_GN_BEACON_SERVICE_TIMER_MAXIMUM+float2int((f_getBsMaxJitter() - 0.0 +1.0)*rnd()) + 0)/1000);
tepelmann's avatar
tepelmann committed
            return v_itsGnBeaconServiceRetransmitTimerMaximum;
         * @desc    Gets the maximum beacon service jitter.
         * @return  Maximum beacon service jitter
        function f_getBsMaxJitter() return float {
            var float v_itsGnBeaconServiceMaxJitter := int2float(PICS_GN_BEACON_SERVICE_MAX_JITTER)/1000.0;
         * @desc    Gets the Lifetime of a Location Table Entry.
         * @return  Lifetime of a Location Table Entry in seconds
         * @see     PICS_GN_LIFETIME_LOC_TE
tepelmann's avatar
tepelmann committed
         */
        function f_getLifetimeLocTableEntry() return float {
            var float v_itsGnLifetimeLocTableEntry := int2float(PICS_GN_LIFETIME_LOC_TE);
            return v_itsGnLifetimeLocTableEntry;
        } // end f_getLifetimeLocTableEntry
berge's avatar
berge committed
        /**
         * @desc    Gets the maximum communication range for CBF algorithm
         * @return  Maximum communication range for CBF algorithm in meters
         * @see     PICS_GN_DEFAULT_MAX_COMMUNICATION_RANGE
berge's avatar
berge committed
         */
        function f_getCbfMaxCommunicationRange() return integer {
            var integer v_maxCommunicationRange := PICS_GN_DEFAULT_MAX_COMMUNICATION_RANGE;
            
            return v_maxCommunicationRange;
        } // end f_getCbfMaxCommunicationRange
        
        function f_getGeoUnicastCbfMaxTime() return integer {
            var integer v_cbfMaxTime := PICS_GN_GEOUNICAST_CBF_MAX_TIME;
            
tepelmann's avatar
tepelmann committed
            return v_cbfMaxTime;
berge's avatar
berge committed
        } // end f_getGeoUnicastCbfMaxTime
berge's avatar
berge committed
        function f_getGeoUnicastCbfMinTime() return integer {
            var integer v_cbfMinTime := PICS_GN_GEOUNICAST_CBF_MIN_TIME;
            
            return v_cbfMinTime;
        } // end f_getGeoUnicastCbfMinTime
        
        function f_getGeoBroadcastCbfMaxTime() return integer {
            var integer v_cbfMaxTime := PICS_GN_GEOBROADCAST_CBF_MAX_TIME;
            
            return v_cbfMaxTime;
        } // end f_getGeoBroadcastCbfMaxTime
        
        function f_getGeoBroadcastCbfMinTime() return integer {
            var integer v_cbfMinTime := PICS_GN_GEOBROADCAST_CBF_MIN_TIME;
            
            return v_cbfMinTime;
        } // end f_getGeoBroadcastCbfMinTime
        
tepelmann's avatar
tepelmann committed
        function f_getGnMaxAreaSize() return float {
            var float v_maxAreaSize := PICS_GN_MAX_GEO_AREA_SIZE;
            
            return v_maxAreaSize;
        } // end f_getGnMaxAreaSize
        
berge's avatar
berge committed
        function f_getAdvancedGbcForwardingMaxCounter() return integer {        
            var integer v_maxCounter := PICS_GN_ADVANCED_BC_FORWARDING_MAX_COUNTER;
            
            return v_maxCounter;  
        }
        
         * @desc    Set the number of neighbour in the Location Table.
         * @see     PX_MIN_NR_NEIGHBOUR
tepelmann's avatar
tepelmann committed
         */
reinaortega's avatar
reinaortega committed
        function f_setNrNeighbourLocTableDefault() runs on ItsGeoNetworking {
fischer's avatar
fischer committed
            var integer v_nrNeighbour := f_random (0, PX_MIN_NR_NEIGHBOUR);
            f_acStartBeaconingMultipleNeighbour(v_nrNeighbour);
            
        } // end f_setNrNeighbourLocTableDefault
         * @desc    Set the number of neighbour in the Location Table (medium).
         * @see     PX_MIN_NR_NEIGHBOUR
         * @see     PX_MAX_NR_NEIGHBOUR
tepelmann's avatar
tepelmann committed
         */
reinaortega's avatar
reinaortega committed
        function f_setNrNeighbourLocTableMedium() runs on ItsGeoNetworking {
            var integer v_nrNeighbour := f_random (PX_MIN_NR_NEIGHBOUR, PX_MAX_NR_NEIGHBOUR);
            
            f_acStartBeaconingMultipleNeighbour(v_nrNeighbour);
            
        } // end f_setNrNeighbourLocTableMedium
         * @desc    Set the number of neighbour in the Location Table (maximum).
         * @see     PX_MAX_NR_NEIGHBOUR
         * @see     PX_MIN_NR_NEIGHBOUR
tepelmann's avatar
tepelmann committed
         */
reinaortega's avatar
reinaortega committed
        function f_setNrNeighbourLocTableMaximum() runs on ItsGeoNetworking {
            var integer v_nrNeighbour := f_random (PX_MAX_NR_NEIGHBOUR, (2*PX_MIN_NR_NEIGHBOUR));
            
            f_acStartBeaconingMultipleNeighbour(v_nrNeighbour);
            
        } // end f_setNrNeighbourLocTableMaximum
berge's avatar
berge committed
    group posVectorFunctions {
        
tepelmann's avatar
tepelmann committed
         * @desc    Convert long position vector to short position vector
         * @param   p_longPosVector Long position vector to be converted
         * @return  Short position vector
berge's avatar
berge committed
        function f_longPosVector2ShortPosVector(in LongPosVector p_longPosVector) return ShortPosVector {
            var ShortPosVector v_shortPosVector;
            
tepelmann's avatar
tepelmann committed
                gnAddr := p_longPosVector.gnAddr,
                timestamp := p_longPosVector.timestamp,
                latitude := p_longPosVector.latitude,
                longitude := p_longPosVector.longitude
            };
            
tepelmann's avatar
tepelmann committed
            return v_shortPosVector;
        /**
         * @desc    Get IUT's long position vector
         * @return  IUT's long position vector
reinaortega's avatar
reinaortega committed
        function f_getIutLongPosVector() runs on ItsBaseGeoNetworking return LongPosVector {
tepelmann's avatar
tepelmann committed
            return f_acGetLongPosVector(f_getIutGnLocalAddress());
        /**
         * @desc    Get IUT's short position vector
         * @return  IUT's short position vector
        function f_getIutShortPosVector() runs on ItsGeoNetworking return ShortPosVector {
            var LongPosVector v_longPosVectorIut := f_getPosition(c_compIut);
            
garciay's avatar
garciay committed
            if (not isbound(v_longPosVectorIut)) {
tepelmann's avatar
tepelmann committed
            return f_longPosVector2ShortPosVector(v_longPosVectorIut);
berge's avatar
berge committed
        /**
tepelmann's avatar
tepelmann committed
         * @desc    Compute a position using a reference position, a distance and an orientation
berge's avatar
berge committed
         * @param   p_iutLongPosVector Reference position
         * @param   p_distance Distance to the reference position (in meter)
         * @param   p_orientation direction of the computed position (0 to 359; 0 means North)
         * @return  LongPosVector
tepelmann's avatar
tepelmann committed
         */
        function f_computePositionUsingDistance(in LongPosVector p_iutLongPosVector, in float p_distance, in integer p_orientation)
berge's avatar
berge committed
        return LongPosVector {
            var LongPosVector v_result := p_iutLongPosVector;
            
            log("*** f_computePositionUsingDistance: INFO: calling fx_computePositionUsingDistance() ***");
            fx_computePositionUsingDistance(p_iutLongPosVector.latitude, p_iutLongPosVector.longitude, p_distance, p_orientation, v_result.latitude, v_result.longitude);
berge's avatar
berge committed
            return v_result;
        }
        
berge's avatar
berge committed
    } // end posVectorFunctions
    
    group externalFunctions {
        /**
         * @desc    External function to compute timestamp based on current time
         * @return  Unix-Epoch-Time mod 2^32
tepelmann's avatar
tepelmann committed
        external function fx_computeGnTimestamp() return UInt32;
        
    } // End of group externalFunctions
    
    group security {
        /**
         * @desc    Waiting for the GN message with Security
         * @param   p_InSecMsg  SecurityMessage template 
         * @param   p_received  returns received SecurityMessage 
         */
        altstep a_securedMessage (
            in template (present) SecuredMessage p_InSecMsg,
            out SecuredMessage p_received
        ) runs on ItsGeoNetworking {
            var GeoNetworkingInd v_geoNw;
            [] geoNetworkingPort.receive(mw_geoNwInd(
                                            mw_geoNwSecPdu(
                                                p_InSecMsg,
                                                mw_geoNwAnyPacket_withPayload(?)
                                        ))) -> value (v_geoNw) {
                    p_received := f_getSecuredMessage(v_geoNw.msgIn);
            }
        }
        
        /**
         * @desc         Receive GN message with security containing certificate as a signer info
         * @param p_cert returns the certificate used for sign received message
         */
        altstep a_securedMessageWithCertificate(
                                                out SecuredMessage p_received
        ) runs on ItsGeoNetworking {
            
            [] a_securedMessage (
                mdw_securedMessage (superset(mw_header_field_signer_info_certificate)),
                // Nothing to do
            }
        } // End of altstep a_securedMessageWithCertificate
        /**
         * @desc         Receive GN message with security containing certificate chain as a signer info
         * @param p_cert returns the certificate used for sign received message
         */
        altstep a_securedMessageWithCertificateChain(
                                                     out SecuredMessage p_received
        ) runs on ItsGeoNetworking {
            [] a_securedMessage (
                    superset(
                        mw_header_field_signer_info_certificate_chain
                )),
                p_received
            ) {
                // Nothing to do
            }
        } // End of altstep a_securedMessageWithCertificateChain
        
        /**
         * @desc         Receive GN message with security containing digest as a signer info
         * @param p_cert returns the certificate used for sign received message
         */
        altstep a_securedMessageWithDigest(
                                           out SecuredMessage p_received
        ) runs on ItsGeoNetworking {
            [] a_securedMessage (
                    superset(
                        mw_header_field_signer_info_digest
                )), 
            ) {
                // Nothing to do
            }
        } // End of altstep a_securedMessageWithDigest
        
    } // End of group altSteps
    group waitingHelpers {
        
        /**
         * @desc  Wait for GN message with security containing certificate as a signer info
         * @return the certificate used for sign received message
         */
        function f_waitForCertificate(
                                      out Certificate p_cert
        ) runs on ItsGeoNetworking return boolean {
            var SecuredMessage v_recv;
            var boolean v_ret := false;
                [] a_securedMessageWithCertificate(v_recv) {
                    if (f_getMsgSignerInfo(v_recv, v_si) == true) { 
                        if (ischosen(v_si.signerInfo.certificate)) {
                            p_cert :=  v_si.signerInfo.certificate;
                            v_ret := true;
                        }
            } // End of 'alt' statement
            
        } // End of function f_waitForCertificate
        /**
         * @desc  Wait for GN message with security containing certificate chain as a signer info
         * @return the certificate used for sign received message
         */
        function f_waitForCertificateChain (out CertificateChain p_chain)
        runs on ItsGeoNetworking
            var SecuredMessage v_recv;
            var boolean v_ret := false;
                [] a_securedMessageWithCertificateChain(v_recv) {
                    if(f_getMsgSignerInfo(v_recv, v_si)) {
                        p_chain :=  v_si.signerInfo.certificates;
                        v_ret := true;
filatov's avatar
filatov committed

        /**
         * @desc  Ask for the certificate chain and wait for GN message with security containing certificate chain as a signer info
         * @return the certificate chain used for sign received message
         */
filatov's avatar
filatov committed
        function f_askForCertificateChain (in template(value) octetstring p_CamPayload)
        runs on ItsGeoNetworking
            var SecuredMessage v_recv;
            var SignerInfo     v_si;
            var boolean v_ret := false;
                [] a_securedMessageWithCertificate(v_recv) {
                    if(f_getMsgSignerInfo(v_recv, v_si)) {
                        if(f_getCertificateSignerInfo(v_si.signerInfo.certificate, v_si)) {
                            if(match (v_si.type_, e_certificate_digest_with_sha256)) {
filatov's avatar
filatov committed
                                f_sendCertificateRequest(v_si.signerInfo.digest, p_CamPayload);
                                if(tc_ac.running) {
filatov's avatar
filatov committed
                                    tc_ac.stop;tc_ac.start;
                                }
                                v_ret := true;
                            }
                        }
                    }
                }
            }
            return v_ret;
        }
        /**
         * @desc  Ask for the certificate chain and wait for GN message with security containing certificate chain as a signer info
         * @return the certificate chain used for sign received message
         */
        function f_askAndWaitForCertificateChain(
                                                 out CertificateChain p_chain, 
                                                 in template(value) octetstring p_CamPayload
        ) runs on ItsGeoNetworking return boolean {
            // Local variables
filatov's avatar
filatov committed
            var SecuredMessage v_recv;
            var SignerInfo     v_si;
            var boolean v_ret := false;
filatov's avatar
filatov committed
            alt {
                [] a_securedMessageWithCertificate(v_recv) {
filatov's avatar
filatov committed
                    if(f_getMsgSignerInfo(v_recv, v_si)) {
                        if(f_getCertificateSignerInfo(v_si.signerInfo.certificate, v_si)) {
                            if(match (v_si.type_, e_certificate_digest_with_sha256)) {
filatov's avatar
filatov committed
                                f_sendCertificateRequest(v_si.signerInfo.digest, p_CamPayload);
                [] a_securedMessageWithCertificateChain(v_recv) {
                    tc_ac.stop;
                    if(f_getMsgSignerInfo(v_recv, v_si) == true) {
                        p_chain := v_si.signerInfo.certificates;
                        v_ret := true;
            } // End of 'alt' statement
            
        } // End of function f_askAndWaitForCertificateChain
filatov's avatar
filatov committed
        
filatov's avatar
filatov committed
        /**
         * @desc  Wait for GN message with security containing digest as a signer info
         * @return the digest of the certificate been used to sign received message
         */
        function f_waitForDigest(
                                 out HashedId8 p_digest
        ) runs on ItsGeoNetworking return boolean {
            // Local variables
filatov's avatar
filatov committed
            var SecuredMessage v_recv;
            var boolean v_ret := false;
filatov's avatar
filatov committed
            alt {
                [] a_securedMessageWithDigest(v_recv) {
                    if(f_getMsgSignerInfo(v_recv, v_si)) { 
                        p_digest :=  v_si.signerInfo.digest;
                        v_ret := true;
filatov's avatar
filatov committed
                }
            } // End of 'alt' statement
            
        } // End of function f_waitForDigest
        /**
         * @desc Send a CAM message with a certificate and wait the certificate chain request message
         * @remark  This function is used only for testing against another ATS
         * @param p_certificate The certificate identifier
         * @param p_CamPayload  The CAM paylaod
         * @return true on success, flase otherwise
         */
        function f_sendCertificateAndWaitForCertificateChainRequest(
                                                                    in charstring p_certificate, 
                                                                    in template(value) octetstring p_CamPayload
        ) runs on ItsGeoNetworking return boolean {
            // Local variables
            var SecuredMessage v_recv;
            
            f_sendCertificate(p_certificate, p_CamPayload);
            alt {
                [] a_securedMessage (
                    mdw_securedMessage(
                        superset(
                            mw_header_field_unrecognised_certificate
                    )),
                    v_recv
                ) {
                    // Nothing to do
                    log("*** " & testcasename() & ": DEBUG: Receive certificate ***")
                }
            } // End of 'alt' statement
            
            return true;
        } // End of function f_sendCertificateAndWaitForCertificateChainRequest
        
    } // End of group waitingHelpers
        
    group CertRequests{
        
        function f_sendCertificateRequest(
                                          in template (value) HashedId8 p_digest,
                                          in template (value) octetstring p_payload
        ) runs on ItsGeoNetworking {
filatov's avatar
filatov committed
            var GeoNetworkingReq v_gnReq;
            var GnNonSecuredPacket v_gnNonSecuredPacket;
            var template (value) ToBeSignedSecuredMessage v_toBeSignedSecuredMessage;
            var template (value) SecuredMessage v_securedMessage;
filatov's avatar
filatov committed
            // Build signed SecuredMessage
garciay's avatar
garciay committed
            v_gnNonSecuredPacket := valueof(m_geoNwShbPacket(
                f_getPosition(c_compNodeC) // FIXME To be verified YANN
garciay's avatar
garciay committed
            ));
filatov's avatar
filatov committed
            // Add CAM payload
garciay's avatar
garciay committed
            v_gnNonSecuredPacket.payload := valueof(f_adaptPayload_m(p_payload));
filatov's avatar
filatov committed
            f_buildGnSecuredCam(
                v_securedMessage,
                m_payload_signed(bit2oct(encvalue(v_gnNonSecuredPacket))),
                e_certificate,
garciay's avatar
garciay committed
                { 
                    m_header_field_unrecognised_certificate(
                        f_HashedId3FromHashedId8(
garciay's avatar
garciay committed
                            valueof(p_digest)
garciay's avatar
garciay committed
                    )) 
                } 
filatov's avatar
filatov committed
            );
                
            // Build secured Gn packet
garciay's avatar
garciay committed
            v_gnReq := valueof(m_geoNwReq_linkLayerBroadcast(
filatov's avatar
filatov committed
                m_geoNwSecPdu(
                    v_gnNonSecuredPacket,
                    v_securedMessage
                ) // End of template m_geoNwSecPdu
garciay's avatar
garciay committed
            )); // End of template m_geoNwReq_linkLayerBroadcast
filatov's avatar
filatov committed
            
            // Send Message
            f_sendGeoNetMessage(v_gnReq);
            
        } // End of function f_sendCertificateRequest
        /**
         * @desc Send a CAM message with a certificate
         * @remark  This function is used only for testing against another ATS
         * @param p_certificate The certificate identifier
         * @param p_CamPayload  The CAM paylaod
         * @return true on success, flase otherwise
         * @see     f_sendCertificateAndWaitForCertificateChainRequest
         */
        function f_sendCertificate(
                                   in charstring p_certificate,
                                   in template (value) octetstring p_payload
        ) runs on ItsGeoNetworking {
            var GeoNetworkingReq v_gnReq;
            var GnNonSecuredPacket v_gnNonSecuredPacket;
            var template (value) ToBeSignedSecuredMessage v_toBeSignedSecuredMessage;
            var template (value) SecuredMessage v_securedMessage;
                
            // Build signed SecuredMessage
            v_gnNonSecuredPacket := valueof(m_geoNwShbPacket(
                f_getPosition(c_compNodeC) // FIXME To be verified YANN
            ));
            // Add CAM payload
            v_gnNonSecuredPacket.payload := valueof(f_adaptPayload_m(p_payload));
            
            f_buildGnSecuredCam(
                v_securedMessage,
                m_payload_signed(bit2oct(encvalue(v_gnNonSecuredPacket))),
                e_certificate,
                -,
                p_certificate
            );
                
            // Build secured Gn packet
            v_gnReq := valueof(m_geoNwReq_linkLayerBroadcast(
                m_geoNwSecPdu(
                    v_gnNonSecuredPacket,
                    v_securedMessage
                ) // End of template m_geoNwSecPdu
            )); // End of template m_geoNwReq_linkLayerBroadcast
            
            // Send Message
            f_sendGeoNetMessage(v_gnReq);
            
        } // End of function f_sendCertificate
        
    } // End of group CertRequests 
    
    group messageGetters {
        
        /**
         * @desc    return SecuredMessage field of GeoNetworking packet 
         * @param   p_msg GeoNetworking packet
         * @return  the SecuredMessage if any
         */
        function f_getSecuredMessage(in GeoNetworkingPdu p_msg)
        return SecuredMessage {
            return p_msg.gnPacket.securedMsg;
        }
        
    }
    
berge's avatar
berge committed
} // end LibItsGeoNetworking_Functions