From e8c40e78efc35ad3c284c494a718b42cffb68b9f Mon Sep 17 00:00:00 2001
From: gauthier <lionel.gauthier@eurecom.fr>
Date: Wed, 4 Nov 2015 10:57:03 +0100
Subject: [PATCH] generated an initial 'generic' scenario.

---
 openair3/TEST/EPC_TEST/generate_scenario.c  |  69 ++++++-
 openair3/TEST/EPC_TEST/generic_scenario.xsl | 214 +++++++++++++++++++-
 2 files changed, 264 insertions(+), 19 deletions(-)

diff --git a/openair3/TEST/EPC_TEST/generate_scenario.c b/openair3/TEST/EPC_TEST/generate_scenario.c
index eff91ea56fc..c5289142b5a 100644
--- a/openair3/TEST/EPC_TEST/generate_scenario.c
+++ b/openair3/TEST/EPC_TEST/generate_scenario.c
@@ -36,6 +36,7 @@
  */
 
 #include <string.h>
+#include <limits.h>
 #include <libconfig.h>
 #include <inttypes.h>
 #include <getopt.h>
@@ -95,7 +96,7 @@
 #define ENB_CONFIG_PROPERTIES_INDEX_OLD 0
 #define ENB_CONFIG_PROPERTIES_INDEX_NEW 1
 
-#define ENB_CONFIG_MAX_XSLT_PARAMS 64
+#define ENB_CONFIG_MAX_XSLT_PARAMS 32
 
 Enb_properties_array_t g_enb_properties[2];
 char                  *g_openair_dir      = NULL;
@@ -136,6 +137,25 @@ int is_file_exists( const char const * file_nameP, const char const *file_roleP)
   return 0;
 }
 
+
+//------------------------------------------------------------------------------
+int strip_extension(char *in_filename)
+{
+  static const uint8_t name_min_len = 1;
+  static const uint8_t max_ext_len = 5; // .pdml !
+  fprintf(stdout, "strip_extension %s\n", in_filename);
+
+  if (NULL != in_filename) {
+    /* Check chars starting at end of string to find last '.' */
+    for (ssize_t i = strlen(in_filename); i > (name_min_len + max_ext_len); i--) {
+      if (in_filename[i] == '.') {
+        in_filename[i] = '\0';
+        return i;
+      }
+    }
+  }
+  return -1;
+}
 //------------------------------------------------------------------------------
 // return number of splitted items
 int split_path( char * pathP, char *** resP)
@@ -155,18 +175,21 @@ int split_path( char * pathP, char *** resP)
 }
 
 //------------------------------------------------------------------------------
-void generate_generic_scenario(const char const * test_nameP, const char const * pdml_in_basenameP)
+int generate_generic_scenario(const char const * test_nameP, const char const * pdml_in_basenameP)
 //------------------------------------------------------------------------------
 {
   //int fd_pdml_in;
   xsltStylesheetPtr cur = NULL;
   xmlDocPtr         doc, res;
-  const char       *params[ENB_CONFIG_MAX_XSLT_PARAMS];
+  FILE             *generic_scenario_file = NULL;
+  const char        generic_scenario_filename[NAME_MAX];
+  const char       *params[2*ENB_CONFIG_MAX_XSLT_PARAMS];
   int               nb_params = 0;
   int               i,j;
   char              astring[1024];
   struct in_addr    addr;
 
+  memset(generic_scenario_filename, 0, sizeof(generic_scenario_filename));
   memset(astring, 0, sizeof(astring));
   if (getcwd(astring, sizeof(astring)) != NULL) {
     fprintf(stdout, "working in %s directory\n", astring);
@@ -182,7 +205,18 @@ void generate_generic_scenario(const char const * test_nameP, const char const *
   xmlSubstituteEntitiesDefault(1);
   xmlLoadExtDtdDefaultValue = 1;
   cur = xsltParseStylesheetFile(astring);
+  if (NULL == cur) {
+    AssertFatal (0, "Could not parse stylesheet file %s (check OPENAIR_DIR env variable)!\n", astring);
+  } else {
+    fprintf(stdout, "XSLT style sheet: %s\n", astring);
+  }
+
   doc = xmlParseFile(pdml_in_basenameP);
+  if (NULL == doc) {
+    AssertFatal (0, "Could not parse pdml file %s!\n", pdml_in_basenameP);
+  } else {
+    fprintf(stdout, "pdml file: %s\n", pdml_in_basenameP);
+  }
   params[nb_params++] = "test_name";
   sprintf(astring, "\"%s\"", test_nameP);
   params[nb_params++] = strdup(astring);
@@ -207,8 +241,25 @@ void generate_generic_scenario(const char const * test_nameP, const char const *
   }
   params[nb_params] = NULL;
   res = xsltApplyStylesheet(cur, doc, params);
-  xsltSaveResultToFile(stdout, res, cur);
-
+  if (NULL != res) {
+    // since pdml filename is not relative (no path), just filename in current directory we can safely remove
+    sprintf(generic_scenario_filename,"%s",pdml_in_basenameP);
+    if (strip_extension(generic_scenario_filename) > 0) {
+      strcat(generic_scenario_filename, "_generic_scenario.xml");
+      generic_scenario_file = fopen( generic_scenario_filename, "w+");
+      if (NULL != generic_scenario_file) {
+        xsltSaveResultToFile(generic_scenario_file, res, cur);
+        fclose(generic_scenario_file);
+        fprintf(stdout, "Wrote generic scenario to %s\n", generic_scenario_filename);
+      } else {
+        fprintf(stderr, "Error in fopen(%s)\n", generic_scenario_filename);
+      }
+    } else {
+      fprintf(stderr, "Error in strip_extension()\n");
+    }
+  } else {
+    fprintf(stderr, "Error in xsltApplyStylesheet()\n");
+  }
   xsltFreeStylesheet(cur);
   xmlFreeDoc(res);
   xmlFreeDoc(doc);
@@ -494,7 +545,7 @@ static void usage (
   fprintf (stdout, "\t-o | --old-enb-conf-file <file>    Provide the old eNB config file for generating a copy of the original test\n");
   fprintf (stdout, "                                     This option is set as many times as there are some eNB config files in the original test\n");
   fprintf (stdout, "\t-p | --pdml             <file>     File name (with no path) of an original scenario that has to be reworked (IP addresses) with new testbed\n");
-  fprintf (stdout, "\t-s | --scenario-generic <file>     File name (with no path) of a  scenario that has to be customized (IP addresses) with new testbed\n");
+  fprintf (stdout, "\t-s | --scenario-generic <file>     File name (with no path) of a scenario that has to be customized (IP addresses) with new testbed\n");
   fprintf (stdout, "\n");
   fprintf (stdout, "\n");
   fprintf (stdout, "Example of generate_scenario use cases:  \n");
@@ -596,7 +647,7 @@ config_parse_opt_line (
   /*
    * Parsing command line
    */
-  while ((option = getopt_long (argc, argv, "hp:n:o:s:t", long_options, NULL)) != -1) {
+  while ((option = getopt_long (argc, argv, "hp:n:o:s:t:", long_options, NULL)) != -1) {
     switch (option) {
       case LONG_OPTION_OLD_ENB_CONF_FILE:
       case 'o':
@@ -669,8 +720,8 @@ config_parse_opt_line (
     if (is_file_exists(old_enb_config_file_name, "Old eNB config file") != GS_IS_FILE) {
       fprintf(stderr, "Error: original eNB config file name %s is not found in dir %s\n", old_enb_config_file_name, g_test_dir);
     }
-    enb_config_display(ENB_CONFIG_PROPERTIES_INDEX_OLD);
     enb_config_init(old_enb_config_file_name, ENB_CONFIG_PROPERTIES_INDEX_OLD);
+    enb_config_display(ENB_CONFIG_PROPERTIES_INDEX_OLD);
 
     if (NULL == pdml_in_file_name) {
       fprintf(stderr, "Error: please provide the PDML file name that should be in %s\n", g_test_dir);
@@ -688,8 +739,8 @@ config_parse_opt_line (
     if (is_file_exists(new_enb_config_file_name, "New eNB config file") != GS_IS_FILE) {
       fprintf(stderr, "Error: New eNB config file name %s is not found in dir %s\n", new_enb_config_file_name, g_test_dir);
     }
-    enb_config_display(ENB_CONFIG_PROPERTIES_INDEX_NEW);
     enb_config_init(new_enb_config_file_name, ENB_CONFIG_PROPERTIES_INDEX_NEW);
+    enb_config_display(ENB_CONFIG_PROPERTIES_INDEX_NEW);
 
     if (NULL == generic_scenario_file_name) {
       fprintf(stderr, "Error: please provide the Generic scenario file name that should be in %s\n", g_test_dir);
diff --git a/openair3/TEST/EPC_TEST/generic_scenario.xsl b/openair3/TEST/EPC_TEST/generic_scenario.xsl
index 99672a28f02..ab0e7f1123a 100644
--- a/openair3/TEST/EPC_TEST/generic_scenario.xsl
+++ b/openair3/TEST/EPC_TEST/generic_scenario.xsl
@@ -8,16 +8,103 @@
    encoding="iso-8859-1"
 />
 
-<xsl:strip-space elements="proto field"/>
+<!-- Ugly but no time to find a better way in XSLT 1.0 (map/list)-->
+ <xsl:param name="enb_s1c0"   select="'0.0.0.0'"/>
+ <xsl:param name="enb_s1c1"   select="'0.0.0.0'"/>
+ <xsl:param name="enb_s1c2"   select="'0.0.0.0'"/>
+ <xsl:param name="enb_s1c3"   select="'0.0.0.0'"/>
+ <xsl:param name="enb_s1c4"   select="'0.0.0.0'"/>
+ <xsl:param name="enb_s1c5"   select="'0.0.0.0'"/>
+ <xsl:param name="enb_s1c6"   select="'0.0.0.0'"/>
+ <xsl:param name="enb_s1c7"   select="'0.0.0.0'"/>
+ <xsl:param name="mme_s1c0_0" select="'0.0.0.0'"/>
+ <xsl:param name="mme_s1c0_1" select="'0.0.0.0'"/>
+ <xsl:param name="mme_s1c0_2" select="'0.0.0.0'"/>
+ <xsl:param name="mme_s1c0_3" select="'0.0.0.0'"/>
+ <xsl:param name="mme_s1c1_0" select="'0.0.0.0'"/>
+ <xsl:param name="mme_s1c1_1" select="'0.0.0.0'"/>
+ <xsl:param name="mme_s1c1_2" select="'0.0.0.0'"/>
+ <xsl:param name="mme_s1c1_3" select="'0.0.0.0'"/>
+ <xsl:param name="mme_s1c2_0" select="'0.0.0.0'"/>
+ <xsl:param name="mme_s1c2_1" select="'0.0.0.0'"/>
+ <xsl:param name="mme_s1c2_2" select="'0.0.0.0'"/>
+ <xsl:param name="mme_s1c2_3" select="'0.0.0.0'"/>
+ <xsl:param name="mme_s1c3_0" select="'0.0.0.0'"/>
+ <xsl:param name="mme_s1c3_1" select="'0.0.0.0'"/>
+ <xsl:param name="mme_s1c3_2" select="'0.0.0.0'"/>
+ <xsl:param name="mme_s1c3_3" select="'0.0.0.0'"/>
+ <xsl:param name="ip_address" select="'0.0.0.0'"/>
 
-<scenario name="{$test_name}">
+
+
+<xsl:template name="reverse_ip">
+  <xsl:param name="ip_address"/>
+    <xsl:choose>
+        <xsl:when test="$ip_address=$enb_s1c0">enb_s1c0</xsl:when>
+        <xsl:when test="$ip_address=$enb_s1c1">enb_s1c1</xsl:when>
+        <xsl:when test="$ip_address=$enb_s1c2">enb_s1c2</xsl:when>
+        <xsl:when test="$ip_address=$enb_s1c3">enb_s1c3</xsl:when>
+        <xsl:when test="$ip_address=$enb_s1c4">enb_s1c4</xsl:when>
+        <xsl:when test="$ip_address=$enb_s1c5">enb_s1c5</xsl:when>
+        <xsl:when test="$ip_address=$mme_s1c0_0">mme_s1c0_0</xsl:when>
+        <xsl:when test="$ip_address=$mme_s1c0_1">mme_s1c0_1</xsl:when>
+        <xsl:when test="$ip_address=$mme_s1c0_2">mme_s1c0_2</xsl:when>
+        <xsl:when test="$ip_address=$mme_s1c0_3">mme_s1c0_3</xsl:when>
+        <xsl:when test="$ip_address=$mme_s1c1_0">mme_s1c1_0</xsl:when>
+        <xsl:when test="$ip_address=$mme_s1c1_1">mme_s1c1_1</xsl:when>
+        <xsl:when test="$ip_address=$mme_s1c1_2">mme_s1c1_2"</xsl:when>
+        <xsl:when test="$ip_address=$mme_s1c1_3">mme_s1c1_3</xsl:when>
+        <xsl:otherwise>reverse_ip_yourself</xsl:otherwise>
+    </xsl:choose> 
+</xsl:template>
+
+<xsl:template name="chunktype2str">
+  <xsl:param name="chunk_type"/>
+    <xsl:choose>
+        <xsl:when test="$chunk_type='00'">DATA</xsl:when>
+        <xsl:when test="$chunk_type='01'">INIT</xsl:when>
+        <xsl:when test="$chunk_type='02'">INIT_ACK</xsl:when>
+        <xsl:when test="$chunk_type='03'">SACK</xsl:when>
+        <xsl:when test="$chunk_type='04'">HEARTBEAT</xsl:when>
+        <xsl:when test="$chunk_type='05'">HEARTBEAT_ACK</xsl:when>
+        <xsl:when test="$chunk_type='06'">ABORT</xsl:when>
+        <xsl:when test="$chunk_type='07'">SHUTDOWN</xsl:when>
+        <xsl:when test="$chunk_type='08'">SHUTDOWN_ACK</xsl:when>
+        <xsl:when test="$chunk_type='09'">ERROR</xsl:when>
+        <xsl:when test="$chunk_type='0a'">COOKIE_ECHO</xsl:when>
+        <xsl:when test="$chunk_type='0b'">COOKIE_ACK</xsl:when>
+        <xsl:when test="$chunk_type='0c'">ECNE</xsl:when>
+        <xsl:when test="$chunk_type='0d'">CWR</xsl:when>
+        <xsl:when test="$chunk_type='0e'">SHUTDOWN_COMPLETE</xsl:when>
+        <xsl:otherwise>UNKNOWN_CHUNK_TYPE</xsl:otherwise>
+    </xsl:choose> 
+</xsl:template>
+
+
+
+
+<xsl:strip-space elements="pdml packet proto field"/>
+
+<xsl:template match="/">
+    <scenario name="{$test_name}">
+        <xsl:apply-templates/>
+    </scenario>
+</xsl:template>
 
 <xsl:template match="proto[@name='frame']">
-    <DEBUG_FRAME>
     <xsl:variable name="time_relative" select="field[@name='frame.time_relative']/@show"/>
     <xsl:variable name="ip" select="proto[@name='ip']"/>
-    <xsl:variable name="ip.src" select="$ip/field[@name='ip.src']/@show"/>
-    <xsl:variable name="ip.dst" select="$ip/field[@name='ip.dst']/@show"/>
+    <xsl:variable name="ip.src">
+        <xsl:call-template name="reverse_ip">
+            <xsl:with-param name="ip_address" select="$ip/field[@name='ip.src']/@show"/>
+        </xsl:call-template>
+    </xsl:variable>
+    <xsl:variable name="ip.dst">
+        <xsl:call-template name="reverse_ip">
+            <xsl:with-param name="ip_address" select="$ip/field[@name='ip.dst']/@show"/>
+        </xsl:call-template>
+    </xsl:variable>
+    
     
     <xsl:for-each select="$ip/proto[@name='sctp']">
         <xsl:variable name="sctp.data_sid"               select="./field[@name='sctp.data_sid']/@show"/>
@@ -25,22 +112,129 @@
         <xsl:variable name="sctp.dstport"                select="./field[@name='sctp.dstport']/@show"/>
         <xsl:variable name="sctp.data_ssn"               select="./field[@name='sctp.data_ssn']/@show"/>
         <xsl:variable name="sctp.data_payload_proto_id"  select="./field[@name='sctp.data_payload_proto_id']/@show"/>
-    
+        <xsl:variable name="sctp.chunk_type_str">
+            <xsl:call-template name="chunktype2str">
+                <xsl:with-param name="chunk_type" select="./field/field[@name='sctp.chunk_type']/@value"/>
+            </xsl:call-template>
+        </xsl:variable>
+        <xsl:variable name="sctp_pos_offset" select="./@pos"/>
+
+        <xsl:choose>
+            <xsl:when test="$sctp.chunk_type_str='DATA'">
         <xsl:for-each select="./proto[@name='s1ap']">
-            <payload name="{ip_dst}">
+            <xsl:variable name="s1ap_pos_offset" select="./@pos"/>
+            <payload name="{$sctp.chunk_type_str}">
                <frame.time_relative        value="{$time_relative}"/>
-               <ip.dst                     value="{$ip.dst}"/>
+               
+               <!-- TODO: pos_offset(substract it from all pos_offsets in s1ap, may depend on which test scenario protocol target S1AP/NAS or NAS only...)-->
+               <pos_offset                 value="{$s1ap_pos_offset}"/>
                <ip.src                     value="{$ip.src}"/>
+               <ip.dst                     value="{$ip.dst}"/>
                <sctp.data_sid              value="{$sctp.data_sid}"/>
                <sctp.srcport               value="{$sctp.srcport}"/>
                <sctp.dstport               value="{$sctp.dstport}"/>
                <sctp.data_ssn              value="{$sctp.data_ssn}"/>
                <sctp.data_payload_proto_id value="{$sctp.data_payload_proto_id}"/>
+               <sctp.chunk_type_str        value="{$sctp.chunk_type_str}"/>
                <xsl:copy-of select="node()"/>
             </payload>
         </xsl:for-each>
+            </xsl:when>
+            <xsl:when test="$sctp.chunk_type_str='INIT'">
+                <xsl:variable name="sctp.init_nr_out_streams"  select="./field/field[@name='sctp.init_nr_out_streams']/@show"/>
+                <xsl:variable name="sctp.init_nr_in_streams"   select="./field/field[@name='sctp.init_nr_in_streams']/@show"/>
+                <xsl:variable name="sctp.init_initial_tsn"     select="./field/field[@name='sctp.init_initial_tsn']/@show"/>
+                <payload name="{$sctp.chunk_type_str}">
+                   <frame.time_relative        value="{$time_relative}"/>
+                   <!-- TODO: pos_offset(substract it from all pos_offsets in s1ap, may depend on which test scenario protocol target S1AP/NAS or NAS only...)-->
+                   <pos_offset                 value="{$sctp_pos_offset}"/>
+                   <ip.src                     value="{$ip.src}"/>
+                   <ip.dst                     value="{$ip.dst}"/>
+                   <sctp.data_sid              value="{$sctp.data_sid}"/>
+                   <sctp.srcport               value="{$sctp.srcport}"/>
+                   <sctp.dstport               value="{$sctp.dstport}"/>
+                   <sctp.init_nr_in_streams    value="{$sctp.init_nr_in_streams}"/>
+                   <sctp.init_nr_out_streams   value="{$sctp.init_nr_out_streams}"/>
+                   <sctp.init_initial_tsn      value="{$sctp.init_initial_tsn}"/>
+                   <sctp.chunk_type_str        value="{$sctp.chunk_type_str}"/>
+                   <!--xsl:copy-of select="node()"/-->
+                </payload>
+            </xsl:when>
+            <xsl:when test="$sctp.chunk_type_str='INIT_ACK'">
+                <xsl:variable name="sctp.initack_nr_out_streams"  select="./field/field[@name='sctp.initack_nr_out_streams']/@show"/>
+                <xsl:variable name="sctp.initack_nr_in_streams"   select="./field/field[@name='sctp.initack_nr_in_streams']/@show"/>
+                <xsl:variable name="sctp.initack_initial_tsn"     select="./field/field[@name='sctp.initack_initial_tsn']/@show"/>
+                <payload name="{$sctp.chunk_type_str}">
+                   <frame.time_relative        value="{$time_relative}"/>
+                   <!-- TODO: pos_offset(substract it from all pos_offsets in s1ap, may depend on which test scenario protocol target S1AP/NAS or NAS only...)-->
+                   <pos_offset                 value="{$sctp_pos_offset}"/>
+                   <ip.src                     value="{$ip.src}"/>
+                   <ip.dst                     value="{$ip.dst}"/>
+                   <sctp.data_sid              value="{$sctp.data_sid}"/>
+                   <sctp.srcport               value="{$sctp.srcport}"/>
+                   <sctp.dstport               value="{$sctp.dstport}"/>
+                   <sctp.initack_nr_in_streams  value="{$sctp.initack_nr_in_streams}"/>
+                   <sctp.initack_nr_out_streams value="{$sctp.initack_nr_out_streams}"/>
+                   <sctp.initack_initial_tsn   value="{$sctp.initack_initial_tsn}"/>
+                   <sctp.chunk_type_str        value="{$sctp.chunk_type_str}"/>
+                   <!--xsl:copy-of select="node()"/-->
+                </payload>
+            </xsl:when>
+            <!--xsl:when test="$sctp.chunk_type_str='SACK'">       </xsl:when-->
+            <!--xsl:when test="$sctp.chunk_type_str='HEARTBEAT'"></xsl:when-->
+            <!--xsl:when test="$sctp.chunk_type_str='HEARTBEAT_ACK'"></xsl:when-->
+            <xsl:when test="$sctp.chunk_type_str='ABORT'">
+                <payload name="{$sctp.chunk_type_str}">
+                   <frame.time_relative        value="{$time_relative}"/>
+                   <!-- TODO: pos_offset(substract it from all pos_offsets in s1ap, may depend on which test scenario protocol target S1AP/NAS or NAS only...)-->
+                   <pos_offset                 value="{$sctp_pos_offset}"/>
+                   <ip.src                     value="{$ip.src}"/>
+                   <ip.dst                     value="{$ip.dst}"/>
+                   <sctp.data_sid              value="{$sctp.data_sid}"/>
+                   <sctp.srcport               value="{$sctp.srcport}"/>
+                   <sctp.dstport               value="{$sctp.dstport}"/>
+                   <sctp.chunk_type_str        value="{$sctp.chunk_type_str}"/>
+                   <xsl:copy-of select="node()"/>
+                </payload>
+            </xsl:when>
+            <xsl:when test="$sctp.chunk_type_str='SHUTDOWN'">
+                <payload name="{$sctp.chunk_type_str}">
+                   <frame.time_relative        value="{$time_relative}"/>
+                   <!-- TODO: pos_offset(substract it from all pos_offsets in s1ap, may depend on which test scenario protocol target S1AP/NAS or NAS only...)-->
+                   <pos_offset                 value="{$sctp_pos_offset}"/>
+                   <ip.src                     value="{$ip.src}"/>
+                   <ip.dst                     value="{$ip.dst}"/>
+                   <sctp.data_sid              value="{$sctp.data_sid}"/>
+                   <sctp.srcport               value="{$sctp.srcport}"/>
+                   <sctp.dstport               value="{$sctp.dstport}"/>
+                   <sctp.chunk_type_str        value="{$sctp.chunk_type_str}"/>
+                   <xsl:copy-of select="node()"/>
+                </payload>
+            </xsl:when>
+            <!--xsl:when test="$sctp.chunk_type_str='SHUTDOWN_ACK'"></xsl:when-->
+            <xsl:when test="$sctp.chunk_type_str='ERROR'">
+                <payload name="{$sctp.chunk_type_str}">
+                   <frame.time_relative        value="{$time_relative}"/>
+                   <!-- TODO: pos_offset(substract it from all pos_offsets in s1ap, may depend on which test scenario protocol target S1AP/NAS or NAS only...)-->
+                   <pos_offset                 value="{$sctp_pos_offset}"/>
+                   <ip.src                     value="{$ip.src}"/>
+                   <ip.dst                     value="{$ip.dst}"/>
+                   <sctp.data_sid              value="{$sctp.data_sid}"/>
+                   <sctp.srcport               value="{$sctp.srcport}"/>
+                   <sctp.dstport               value="{$sctp.dstport}"/>
+                   <sctp.chunk_type_str        value="{$sctp.chunk_type_str}"/>
+                   <xsl:copy-of select="node()"/>
+                </payload>
+            </xsl:when>
+            <!--xsl:when test="$sctp.chunk_type_str='COOKIE_ECHO'">            </xsl:when-->
+            <!--xsl:when test="$sctp.chunk_type_str='COOKIE_ACK'">            </xsl:when-->
+            <!--xsl:when test="$sctp.chunk_type_str='ECNE'">            </xsl:when-->
+            <!--xsl:when test="$sctp.chunk_type_str='CWR'">            </xsl:when-->
+            <!--xsl:when test="$sctp.chunk_type_str='SHUTDOWN_COMPLETE'">            </xsl:when-->
+            <xsl:otherwise></xsl:otherwise>
+        </xsl:choose> 
+
+        
     </xsl:for-each>
-    </DEBUG_FRAME>
 </xsl:template>
-</scenario>
 </xsl:stylesheet>
-- 
GitLab