/******************************************************************************
* Copyright (c) 2000-2019 Ericsson Telecom AB
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v2.0
* which accompanies this distribution, and is available at
* https://www.eclipse.org/org/documents/epl-2.0/EPL-2.0.html
*
* Contributors:
* Gabor Tatarka
* Gabor Szalai
* Jozsef Gyurusi
* Laszlo Skumat
******************************************************************************/
//
//  File:               Socket_API_Definitions.ttcn
//  Prodnr:             CNL 113 686


module Socket_API_Definitions {  

  /* The connection ID is a test port component level unique identifier of the
     connection.
     It is returned by the listen and connect functions and in the connOpened
     event. It identifies the connection in subsequent function calls and in
     sent or received events.
     The SCTP protocol supports one-to-many connections on one socket,
     which requires also an association ID besides the connection ID.
  */
  type integer ConnectionId;
  type record of ConnectionId ro_ConnectionId;
  type integer AssociationId;
  type record of AssociationId ro_AssociationId;

  /* IP address version 4 or 6 is accepted in the dotted format.
     Examples:
     IPv4: 192.168.0.1
     IPv6: fe80::211:d8ff:fe51:4cca
     Host name can also be used instead of IP address.
  */
  type charstring HostName;
  type integer PortNumber;
  type record Socket {
    HostName hostName,
    PortNumber portNumber
  }
  type record of Socket SocketList;

  /* ANY_ADDR and ANY_PORT constants */
  const HostName c_ipv4AnyAddr := "0.0.0.0";
  const HostName c_ipv6AnyAddr := "::";
  const PortNumber c_anyPort := 0;
  const HostName c_defaultLocAddr := "";
  const PortNumber c_defaultLocPort := -1;

  /* The protocol (TCP, UDP, UDPLight or SCTP) has to be specified in the first
     connection creation operation: either in listen or connect.
     In subsequent operations the protocol is determined by the connection ID,
     therefore it should be omitted, but it is accepted for backward
     compatibility. If protocol is specified, then it is checked.
  */
  type record UdpTuple {}
  type record UdpLightTuple {}
  type record TcpTuple {}
  type record SctpTuple {
    /* Specifies the stream number of the message. */  
    integer sinfo_stream optional,
    /* Specifies the information that is passed by the upper layer in 
       the peer application. */      
    integer sinfo_ppid optional,
    /* Multiple remote addresses can be given in case of one-to-many
       connections. */
    SocketList remSocks optional,
    /* Association ID to identify one specific connection in case of
       one-to-many connections. */
    AssociationId assocId optional
  }
  type record SslTuple {}
  // DTLS works over UDP or SCTP (Datagram TLS)
  // SCTP is not supported -> CR if needed
  type union DtlsTuple {
    UdpTuple udp,
    SctpTuple sctp
  }
  type record UnspecifiedTuple {}

  type union ProtoTuple {
    UdpTuple udp,
    UdpLightTuple udpLight,
    TcpTuple tcp,
    SctpTuple sctp,
    SslTuple ssl,
    DtlsTuple dtls,
    UnspecifiedTuple unspecified
  }

  type integer UserData;

  /* PortEvent is used to inform the upper layer about asynchronous events.
     Notification is sent if connection opened during listenning or when
     connection is closed.
     PortEvent is also used for notification about results of operations,
     that need to be handled by the upper layer.
     This can be a notification about an error or
     a notification that an operation (connect or send) on a connection should
     be retried later or that a deferred operation is no possible.
     The result event contains the connection ID besides the error code.
  */

  type enumerated PortError {
    ERROR_GENERAL,
    ERROR_INSUFFICIENT_MEMORY,
    ERROR_INVALID_INPUT_PARAMETER,
    ERROR_UNSUPPORTED_PROTOCOL,
    ERROR_SOCKET,
    ERROR_HOSTNAME,
    ERROR_INVALID_CONNECTION,
    ERROR_TEMPORARILY_UNAVAILABLE,
    ERROR_AVAILABLE,
    ERROR_LENGTH
  }

  type record Result {
    PortError errorCode optional,
    ConnectionId connId optional,
    integer os_error_code optional,
    charstring os_error_text optional
  }

  type record Extended_Result {
    PortError errorCode optional,
    ConnectionId connId optional,
    integer os_error_code optional,
    charstring os_error_text optional,
    octetstring  msg optional
  }


  type record ConnectionOpenedEvent {
    ConnectionId connId,
    HostName remName,
    PortNumber remPort,
    HostName locName,
    PortNumber locPort,
    ProtoTuple proto,
    UserData userData
  }

  type ConnectionOpenedEvent ConnectionClosedEvent;
  
   type union SctpEvent {
     SctpAssocChange sctpAssocChange,
     SctpPeerAddrChange sctpPeerAddrChange,
     SctpSendFailed sctpSendFailed,
     SctpRemoteError sctpRemoteError,
     SctpShutDownEvent sctpShutDownEvent,
     SctpPartialDeliveryEvent sctpPartialDeliveryEvent,
     SctpAdaptationIndication sctpAdaptationIndication,
     SctpSenderDryEvent sctpSenderDryEvent
   }

   type union PortEvent {
     ConnectionOpenedEvent connOpened,
     ConnectionClosedEvent connClosed,
     Result result,
     Extended_Result extended_result,
     SctpEvent sctpEvent
   }
   
   /* SCTP type events */
   type enumerated SAC_STATE {
     SCTP_COMM_UP, SCTP_COMM_LOST, SCTP_RESTART, 
     SCTP_SHUTDOWN_COMP, SCTP_CANT_STR_ASSOC, SCTP_UNKNOWN_SAC_STATE
   }
 
   type record SctpAssocChange {
     integer clientId,
     ProtoTuple proto,
     SAC_STATE sac_state
   }
 
   type enumerated SPC_STATE {
     SCTP_ADDR_AVAILABLE, SCTP_ADDR_UNREACHABLE, SCTP_ADDR_REMOVED,
     SCTP_ADDR_ADDED, SCTP_ADDR_MADE_PRIM, SCTP_ADDR_CONFIRMED, SCTP_UNKNOWN_SPC_STATE
   }
 
   type record SctpPeerAddrChange {
     integer clientId,
     SPC_STATE spc_state
   }
 
   type record SctpSendFailed {
     integer clientId
   }
 
   type record SctpRemoteError {
     integer clientId
   }
 
   type record SctpShutDownEvent {
     integer clientId
   }
 
   type record SctpPartialDeliveryEvent {
     integer clientId
   }
 
   type record SctpAdaptationIndication {
     integer clientId
   } 
    
   type record SctpSenderDryEvent {
     integer clientId
   } 
   /* SCTP type events end*/ 

  type record of integer ro_integer;

  /* Type definition for the user defined function to determine the message
     length (boundary) in a TCP data stream.
  */
  type function f_getMsgLen(
    in octetstring stream,
    inout ro_integer args // variadic list of user defined parameters
  )
  runs on self
  return integer;

  type record of charstring ro_charstring;

  /* 
    Type definition to query parameters.
  */

//   type integer PortParam; // (PortParamMin..PortParamMax);
//   const integer PortParamMin := 0
//   const integer LOCALADDRESS := 0;
//   const integer REMOTEADDRESS := 1;
//   const integer PROTO := 2;
//   const integer USERDATA := 3;
//   const integer PARENTIDX := 4;
//   const integer PortParamMax := 4;
// 
//   type union PortParamResult {
//     Socket local,
//     Socket remote,
//     ProtoTuple proto,
//     integer userData,
//     ConnectionId parentIdx
//   }

} // module Socket_API_Definitions

