Use MAC address documentation range in filter examples
[metze/wireshark/wip.git] / epan / dissectors / packet-fcswils.c
index 3e6429d4d2d0141378dc67fa6eabaea6d50b9327..81a11dcd2fc8ee3ccbfa4fdb5696213e2991aa48 100644 (file)
@@ -1,4 +1,4 @@
-/* packet-fcswils
+/* packet-fcswils.c
  * Routines for FC Inter-switch link services
  * Copyright 2001, Dinesh G Dutt <ddutt@cisco.com>
  *
 
 #include "config.h"
 
-#include <glib.h>
-
 #include <epan/packet.h>
+#include <epan/expert.h>
 #include <epan/to_str.h>
-#include <epan/wmem/wmem.h>
-#include <epan/conversation.h>
-#include <epan/etypes.h>
 #include "packet-fc.h"
 #include "packet-fcswils.h"
 #include "packet-fcct.h"
@@ -127,6 +123,9 @@ static int hf_swils_zone_objtype          = -1;
 static int hf_swils_zone_mbrtype          = -1;
 static int hf_swils_zone_protocol         = -1;
 static int hf_swils_zone_mbrid            = -1;
+static int hf_swils_zone_mbrid_fcwwn      = -1;
+static int hf_swils_zone_mbrid_fc         = -1;
+static int hf_swils_zone_mbrid_uint       = -1;
 static int hf_swils_zone_status           = -1;
 static int hf_swils_zone_reason           = -1;
 static int hf_swils_aca_domainid          = -1;
@@ -179,6 +178,34 @@ static int hf_swils_ess_fzs_defzone       = -1;
 static int hf_swils_ess_cap_len           = -1;
 static int hf_swils_mrra_vendorinfo       = -1;
 
+/* Generated from convert_proto_tree_add_text.pl */
+static int hf_swils_lsrh_lsr_age = -1;
+static int hf_swils_zone_full_zone_set_length = -1;
+static int hf_swils_zone_num_zoning_objects = -1;
+static int hf_swils_lsrec_number_of_links = -1;
+static int hf_swils_sfc_zoneset_length = -1;
+static int hf_swils_zone_vendor_unique = -1;
+static int hf_swils_zone_num_members = -1;
+static int hf_swils_zone_active_zoneset_length = -1;
+static int hf_swils_lsack_num_of_lsr_headers = -1;
+static int hf_swils_lsrh_lsr_length = -1;
+static int hf_swils_esc_payload_length = -1;
+static int hf_swils_lsupdate_num_of_lsrs = -1;
+static int hf_swils_zone_mbr_identifier_length = -1;
+static int hf_swils_zone_mbrflags = -1;
+static int hf_swils_lsrh_options = -1;
+static int hf_swils_domain_id_list_length = -1;
+static int hf_swils_lsack_flags = -1;
+static int hf_swils_rscn_num_entries = -1;
+static int hf_swils_requested_domain_id = -1;
+static int hf_swils_lsrh_checksum = -1;
+static int hf_swils_granted_domain_id = -1;
+static int hf_swils_lsupdate_flags = -1;
+
+
+static expert_field ei_swils_efp_record_len = EI_INIT;
+static expert_field ei_swils_no_exchange = EI_INIT;
+static expert_field ei_swils_zone_mbrid = EI_INIT;
 
 /* Initialize the subtree pointers */
 static gint ett_fcswils             = -1;
@@ -420,7 +447,7 @@ typedef struct _fcswils_conv_data {
 static GHashTable *fcswils_req_hash = NULL;
 
 /* list of commands for each commandset */
-typedef void (*fcswils_dissector_t)(tvbuff_t *tvb, proto_tree *tree, guint8 isreq);
+typedef void (*fcswils_dissector_t)(tvbuff_t *tvb, packet_info* pinfo, proto_tree *tree, guint8 isreq);
 
 typedef struct _fcswils_func_table_t {
     fcswils_dissector_t func;
@@ -459,11 +486,13 @@ fcswils_hash(gconstpointer v)
 static void
 fcswils_init_protocol(void)
 {
-    if (fcswils_req_hash)
-        g_hash_table_destroy(fcswils_req_hash);
-
     fcswils_req_hash = g_hash_table_new(fcswils_hash, fcswils_equal);
+}
 
+static void
+fcswils_cleanup_protocol(void)
+{
+    g_hash_table_destroy(fcswils_req_hash);
 }
 
 static guint8 *
@@ -685,7 +714,7 @@ dissect_swils_ess_capability_obj(tvbuff_t *tvb, proto_tree *tree, int offset)
 }
 
 static void
-dissect_swils_nullpayload(tvbuff_t *tvb _U_, proto_tree *tree _U_,
+dissect_swils_nullpayload(tvbuff_t *tvb _U_, packet_info* pinfo _U_, proto_tree *tree _U_,
                           guint8 isreq _U_)
 {
     /* Common dissector for those ILSs without a payload */
@@ -693,43 +722,40 @@ dissect_swils_nullpayload(tvbuff_t *tvb _U_, proto_tree *tree _U_,
 }
 
 static void
-dissect_swils_elp(tvbuff_t *tvb, proto_tree *elp_tree, guint8 isreq _U_)
+dissect_swils_elp(tvbuff_t *tvb, packet_info* pinfo _U_, proto_tree *elp_tree, guint8 isreq _U_)
 {
 
     /* Set up structures needed to add the protocol subtree and manage it */
-    int          offset = 0;
-    const gchar *flags;
-    fcswils_elp  elp;
-
     /* Response i.e. SW_ACC for an ELP has the same format as the request */
     /* We skip the initial 4 bytes as we don't care about the opcode */
-    tvb_memcpy(tvb, (guint8 *)&elp, 4, FC_SWILS_ELP_SIZE);
-
-    elp.r_a_tov = g_ntohl(elp.r_a_tov);
-    elp.e_d_tov = g_ntohl(elp.e_d_tov);
-    elp.isl_flwctrl_mode = g_ntohs(elp.isl_flwctrl_mode);
-    elp.flw_ctrl_parmlen = g_ntohs(elp.flw_ctrl_parmlen);
+    int          offset = 4;
+    const gchar *flags;
+    guint32 r_a_tov;
+    guint32 e_d_tov;
+    guint16 isl_flwctrl_mode;
+    guint8  clsf_svcparm[6], cls1_svcparm[2], cls2_svcparm[2], cls3_svcparm[2];
 
     if (elp_tree) {
         offset += 4;
         proto_tree_add_item(elp_tree, hf_swils_elp_rev, tvb, offset++, 1, ENC_BIG_ENDIAN);
         proto_tree_add_item(elp_tree, hf_swils_elp_flags, tvb, offset, 2, ENC_NA);
         offset += 3;
+        r_a_tov = tvb_get_ntohl(tvb, offset);
         proto_tree_add_uint_format_value(elp_tree, hf_swils_elp_r_a_tov, tvb, offset, 4,
-                                   elp.r_a_tov, "%d msecs", elp.r_a_tov);
+                                   r_a_tov, "%d msecs", r_a_tov);
         offset += 4;
+        e_d_tov = tvb_get_ntohl(tvb, offset);
         proto_tree_add_uint_format_value(elp_tree, hf_swils_elp_e_d_tov, tvb, offset, 4,
-                                   elp.e_d_tov, "%d msecs", elp.e_d_tov);
+                                   e_d_tov, "%d msecs", e_d_tov);
         offset += 4;
-        proto_tree_add_string(elp_tree, hf_swils_elp_req_epn, tvb, offset, 8,
-                              fcwwn_to_str(elp.req_epname));
+        proto_tree_add_item(elp_tree, hf_swils_elp_req_epn, tvb, offset, 8, ENC_NA);
         offset += 8;
-        proto_tree_add_string(elp_tree, hf_swils_elp_req_esn, tvb, offset, 8,
-                              fcwwn_to_str(elp.req_sname));
+        proto_tree_add_item(elp_tree, hf_swils_elp_req_esn, tvb, offset, 8, ENC_NA);
         offset += 8;
 
-        if (elp.clsf_svcparm[0] & 0x80) {
-            if (elp.clsf_svcparm[4] & 0x20) {
+        tvb_memcpy(tvb, clsf_svcparm, offset, 6);
+        if (clsf_svcparm[0] & 0x80) {
+            if (clsf_svcparm[4] & 0x20) {
                 flags="Class F Valid | X_ID Interlock";
             } else {
                 flags="Class F Valid | No X_ID Interlk";
@@ -738,7 +764,7 @@ dissect_swils_elp(tvbuff_t *tvb, proto_tree *elp_tree, guint8 isreq _U_)
             flags="Class F Invld";
         }
         proto_tree_add_bytes_format_value(elp_tree, hf_swils_elp_clsf_svcp, tvb, offset, 6,
-                                    &elp.clsf_svcparm[0], "(%s)", flags);
+                                    clsf_svcparm, "(%s)", flags);
         offset += 6;
 
         proto_tree_add_item(elp_tree, hf_swils_elp_clsf_rcvsz, tvb, offset, 2, ENC_BIG_ENDIAN);
@@ -750,7 +776,8 @@ dissect_swils_elp(tvbuff_t *tvb, proto_tree *elp_tree, guint8 isreq _U_)
         proto_tree_add_item(elp_tree, hf_swils_elp_clsf_openseq, tvb, offset, 2, ENC_BIG_ENDIAN);
         offset += 4;
 
-        if (elp.cls1_svcparm[0] & 0x80) {
+        tvb_memcpy(tvb, cls1_svcparm, offset, 2);
+        if (cls1_svcparm[0] & 0x80) {
 #define MAX_FLAGS_LEN 40
             char *flagsbuf;
             gint stroff, returned_length;
@@ -761,15 +788,15 @@ dissect_swils_elp(tvbuff_t *tvb, proto_tree *elp_tree, guint8 isreq _U_)
             returned_length = g_snprintf(flagsbuf+stroff, MAX_FLAGS_LEN-stroff,
                                          "Class 1 Valid");
             stroff += MIN(returned_length, MAX_FLAGS_LEN-stroff);
-            if (elp.cls1_svcparm[0] & 0x40) {
+            if (cls1_svcparm[0] & 0x40) {
                 returned_length = g_snprintf(flagsbuf+stroff, MAX_FLAGS_LEN-stroff, " | IMX");
                 stroff += MIN(returned_length, MAX_FLAGS_LEN-stroff);
             }
-            if (elp.cls1_svcparm[0] & 0x20) {
+            if (cls1_svcparm[0] & 0x20) {
                 returned_length = g_snprintf(flagsbuf+stroff, MAX_FLAGS_LEN-stroff, " | IPS");
                 stroff += MIN(returned_length, MAX_FLAGS_LEN-stroff);
             }
-            if (elp.cls1_svcparm[0] & 0x10) {
+            if (cls1_svcparm[0] & 0x10) {
                 /*returned_length =*/ g_snprintf(flagsbuf+stroff, MAX_FLAGS_LEN-stroff, " | LKS");
             }
             flags=flagsbuf;
@@ -781,13 +808,14 @@ dissect_swils_elp(tvbuff_t *tvb, proto_tree *elp_tree, guint8 isreq _U_)
         proto_tree_add_bytes_format_value(elp_tree, hf_swils_elp_cls1_svcp, tvb, offset, 2,
                                     NULL, "(%s)", flags);
         offset += 2;
-        if (elp.cls1_svcparm[0] & 0x80) {
+        if (cls1_svcparm[0] & 0x80) {
             proto_tree_add_item(elp_tree, hf_swils_elp_cls1_rcvsz, tvb, offset, 2, ENC_BIG_ENDIAN);
         }
         offset += 2;
 
-        if (elp.cls2_svcparm[0] & 0x80) {
-            if (elp.cls2_svcparm[0] & 0x08) {
+        tvb_memcpy(tvb, cls2_svcparm, offset, 2);
+        if (cls2_svcparm[0] & 0x80) {
+            if (cls2_svcparm[0] & 0x08) {
                 flags="Class 2 Valid | Seq Delivery";
             }
             else {
@@ -799,17 +827,18 @@ dissect_swils_elp(tvbuff_t *tvb, proto_tree *elp_tree, guint8 isreq _U_)
         }
 
         proto_tree_add_bytes_format_value(elp_tree, hf_swils_elp_cls2_svcp, tvb, offset, 2,
-                                    &elp.cls2_svcparm[0],
+                                    cls2_svcparm,
                                     "(%s)", flags);
         offset += 2;
 
-        if (elp.cls2_svcparm[0] & 0x80) {
+        if (cls2_svcparm[0] & 0x80) {
             proto_tree_add_item(elp_tree, hf_swils_elp_cls2_rcvsz, tvb, offset, 2, ENC_BIG_ENDIAN);
         }
         offset += 2;
 
-        if (elp.cls3_svcparm[0] & 0x80) {
-            if (elp.cls3_svcparm[0] & 0x08) {
+        tvb_memcpy(tvb, cls3_svcparm, offset, 2);
+        if (cls3_svcparm[0] & 0x80) {
+            if (cls3_svcparm[0] & 0x08) {
                 flags="Class 3 Valid | Seq Delivery";
             }
             else {
@@ -820,17 +849,18 @@ dissect_swils_elp(tvbuff_t *tvb, proto_tree *elp_tree, guint8 isreq _U_)
             flags="Class 3 Invld";
         }
         proto_tree_add_bytes_format_value(elp_tree, hf_swils_elp_cls3_svcp, tvb, offset, 2,
-                                    &elp.cls3_svcparm[0],
+                                    cls3_svcparm,
                                     "(%s)", flags);
         offset += 2;
 
-        if (elp.cls3_svcparm[0] & 0x80) {
+        if (cls3_svcparm[0] & 0x80) {
             proto_tree_add_item(elp_tree, hf_swils_elp_cls3_rcvsz, tvb, offset, 2, ENC_BIG_ENDIAN);
         }
         offset += 22;
 
+        isl_flwctrl_mode = tvb_get_ntohs(tvb, offset);
         proto_tree_add_string(elp_tree, hf_swils_elp_isl_fc_mode, tvb, offset, 2,
-                              val_to_str_const(elp.isl_flwctrl_mode, fcswils_elp_fc_val, "Vendor Unique"));
+                              val_to_str_const(isl_flwctrl_mode, fcswils_elp_fc_val, "Vendor Unique"));
         offset += 2;
         proto_tree_add_item(elp_tree, hf_swils_elp_fcplen, tvb, offset, 2, ENC_BIG_ENDIAN);
         offset += 2;
@@ -848,50 +878,44 @@ dissect_swils_elp(tvbuff_t *tvb, proto_tree *elp_tree, guint8 isreq _U_)
 }
 
 static void
-dissect_swils_efp(tvbuff_t *tvb, proto_tree *efp_tree, guint8 isreq _U_)
+dissect_swils_efp(tvbuff_t *tvb, packet_info* pinfo, proto_tree *efp_tree, guint8 isreq _U_)
 {
 
 /* Set up structures needed to add the protocol subtree and manage it */
     proto_tree  *lrec_tree;
+    proto_item  *rec_item;
     int          num_listrec = 0;
-    int          offset      = 0;
-    fcswils_efp  efp;
+    int          offset      = 1; /* Skip opcode */
+    guint8       reclen;
+    guint16      payload_len;
     guint8       rec_type;
 
+    reclen = tvb_get_guint8(tvb, offset);
+    rec_item = proto_tree_add_uint(efp_tree, hf_swils_efp_record_len, tvb, offset, 1, reclen);
     offset += 1;
-    efp.reclen = tvb_get_guint8(tvb, offset);
-    if (efp_tree)
-        proto_tree_add_uint(efp_tree, hf_swils_efp_record_len, tvb, offset, 1, efp.reclen);
-    offset += 1;
-    efp.payload_len = tvb_get_ntohs(tvb, offset);
-    if (efp.payload_len < FC_SWILS_EFP_SIZE) {
-        if (efp_tree)
-            proto_tree_add_uint_format_value(efp_tree, hf_swils_efp_payload_len,
-                                       tvb, offset, 2, efp.payload_len,
+    payload_len = tvb_get_ntohs(tvb, offset);
+    if (payload_len < FC_SWILS_EFP_SIZE) {
+        proto_tree_add_uint_format_value(efp_tree, hf_swils_efp_payload_len,
+                                       tvb, offset, 2, payload_len,
                                        "%u (bogus, must be >= %u)",
-                                       efp.payload_len, FC_SWILS_EFP_SIZE);
+                                       payload_len, FC_SWILS_EFP_SIZE);
         return;
     }
-    if (efp_tree)
-        proto_tree_add_item(efp_tree, hf_swils_efp_payload_len, tvb, offset, 2, ENC_BIG_ENDIAN);
+    proto_tree_add_item(efp_tree, hf_swils_efp_payload_len, tvb, offset, 2, ENC_BIG_ENDIAN);
     offset += 5;       /* skip 3 reserved bytes, too */
-    if (efp_tree)
-        proto_tree_add_item(efp_tree, hf_swils_efp_pswitch_pri, tvb,
+    proto_tree_add_item(efp_tree, hf_swils_efp_pswitch_pri, tvb,
                             offset, 1, ENC_BIG_ENDIAN);
     offset += 1;
-    tvb_memcpy(tvb, efp.pswitch_name, offset, 8);
-    if (efp_tree)
-        proto_tree_add_string(efp_tree, hf_swils_efp_pswitch_name, tvb, offset,
-                              8, fcwwn_to_str(efp.pswitch_name));
+    proto_tree_add_item(efp_tree, hf_swils_efp_pswitch_name, tvb, offset, 8, ENC_NA);
     offset += 8;
 
+    if (reclen == 0) {
+        expert_add_info(pinfo, rec_item, &ei_swils_efp_record_len);
+        return;
+    }
     /* Add List Records now */
     if (efp_tree) {
-        if (efp.reclen == 0) {
-            proto_tree_add_text(efp_tree, tvb, 0, 0, "Record length is zero");
-            return;
-        }
-        num_listrec = (efp.payload_len - FC_SWILS_EFP_SIZE)/efp.reclen;
+        num_listrec = (payload_len - FC_SWILS_EFP_SIZE)/reclen;
         while (num_listrec-- > 0) {
             rec_type = tvb_get_guint8(tvb, offset);
             lrec_tree = proto_tree_add_subtree(efp_tree, tvb, offset, -1,
@@ -905,33 +929,32 @@ dissect_swils_efp(tvbuff_t *tvb, proto_tree *efp_tree, guint8 isreq _U_)
 
             case FC_SWILS_LRECTYPE_DOMAIN:
                 proto_tree_add_item(lrec_tree, hf_swils_efp_dom_id, tvb, offset+1, 1, ENC_BIG_ENDIAN);
-                proto_tree_add_string(lrec_tree, hf_swils_efp_switch_name, tvb, offset+8, 8,
-                                      tvb_fcwwn_to_str(tvb, offset+8));
+                proto_tree_add_item(lrec_tree, hf_swils_efp_switch_name, tvb, offset+8, 8, ENC_NA);
                 break;
 
             case FC_SWILS_LRECTYPE_MCAST:
                 proto_tree_add_item(lrec_tree, hf_swils_efp_mcast_grpno, tvb, offset+1, 1, ENC_BIG_ENDIAN);
                 break;
             }
-            offset += efp.reclen;
+            offset += reclen;
         }
     }
 }
 
 static void
-dissect_swils_dia(tvbuff_t *tvb, proto_tree *dia_tree, guint8 isreq _U_)
+dissect_swils_dia(tvbuff_t *tvb, packet_info* pinfo _U_, proto_tree *dia_tree, guint8 isreq _U_)
 {
     /* Set up structures needed to add the protocol subtree and manage it */
     int offset = 0;
 
     if (dia_tree) {
-        proto_tree_add_string(dia_tree, hf_swils_dia_switch_name, tvb, offset+4,
-                              8, tvb_fcwwn_to_str(tvb, offset+4));
+        proto_tree_add_item(dia_tree, hf_swils_dia_switch_name, tvb, offset+4,
+                              8, ENC_NA);
     }
 }
 
 static void
-dissect_swils_rdi(tvbuff_t *tvb, proto_tree *rdi_tree, guint8 isreq)
+dissect_swils_rdi(tvbuff_t *tvb, packet_info* pinfo _U_, proto_tree *rdi_tree, guint8 isreq)
 {
     /* Set up structures needed to add the protocol subtree and manage it */
     int offset = 0;
@@ -941,8 +964,7 @@ dissect_swils_rdi(tvbuff_t *tvb, proto_tree *rdi_tree, guint8 isreq)
         plen = tvb_get_ntohs(tvb, offset+2);
 
         proto_tree_add_item(rdi_tree, hf_swils_rdi_payload_len, tvb, offset+2, 2, ENC_BIG_ENDIAN);
-        proto_tree_add_string(rdi_tree, hf_swils_rdi_req_sname, tvb, offset+4,
-                              8, tvb_fcwwn_to_str(tvb, offset+4));
+        proto_tree_add_item(rdi_tree, hf_swils_rdi_req_sname, tvb, offset+4, 8, ENC_NA);
 
         /* 12 is the length of the initial header and 4 is the size of each
          * domain request record.
@@ -951,14 +973,10 @@ dissect_swils_rdi(tvbuff_t *tvb, proto_tree *rdi_tree, guint8 isreq)
         offset = 12;
         for (i = 0; i < numrec; i++) {
             if (isreq) {
-                proto_tree_add_text(rdi_tree, tvb, offset+3, 1,
-                                    "Requested Domain ID: %d",
-                                    tvb_get_guint8(tvb, offset+3));
+                proto_tree_add_item(rdi_tree, hf_swils_requested_domain_id, tvb, offset+3, 1, ENC_BIG_ENDIAN);
             }
             else {
-                proto_tree_add_text(rdi_tree, tvb, offset+3, 1,
-                                    "Granted Domain ID: %d",
-                                    tvb_get_guint8(tvb, offset+3));
+                proto_tree_add_item(rdi_tree, hf_swils_granted_domain_id, tvb, offset+3, 1, ENC_BIG_ENDIAN);
             }
             offset += 4;
         }
@@ -991,24 +1009,20 @@ static void
 dissect_swils_fspf_lsrechdr(tvbuff_t *tvb, proto_tree *tree, int offset)
 {
     proto_tree_add_item(tree, hf_swils_lsrh_lsr_type, tvb, offset, 1, ENC_BIG_ENDIAN);
-    proto_tree_add_text(tree, tvb, offset+2, 2, "LSR Age: %d secs",
-                        tvb_get_ntohs(tvb, offset+2));
-    proto_tree_add_text(tree, tvb, offset+4, 4, "Options : 0x%x",
-                        tvb_get_ntohl(tvb, offset+4));
+    proto_tree_add_uint_format_value(tree, hf_swils_lsrh_lsr_age, tvb, offset+2, 2,
+                        tvb_get_ntohs(tvb, offset+2), "%d secs", tvb_get_ntohs(tvb, offset+2));
+    proto_tree_add_item(tree, hf_swils_lsrh_options, tvb, offset+4, 4, ENC_BIG_ENDIAN);
     proto_tree_add_item(tree, hf_swils_lsrh_lsid, tvb, offset+11, 1, ENC_BIG_ENDIAN);
     proto_tree_add_item(tree, hf_swils_lsrh_adv_domid, tvb, offset+15, 1, ENC_BIG_ENDIAN);
     proto_tree_add_item(tree, hf_swils_lsrh_ls_incid, tvb, offset+16, 4, ENC_BIG_ENDIAN);
-    proto_tree_add_text(tree, tvb, offset+20, 2, "Checksum: 0x%x",
-                        tvb_get_ntohs(tvb, offset+20));
-    proto_tree_add_text(tree, tvb, offset+22, 2, "LSR Length: %d",
-                        tvb_get_ntohs(tvb, offset+22));
+    proto_tree_add_item(tree, hf_swils_lsrh_checksum, tvb, offset+20, 2, ENC_BIG_ENDIAN);
+    proto_tree_add_item(tree, hf_swils_lsrh_lsr_length, tvb, offset+22, 2, ENC_BIG_ENDIAN);
 }
 
 static void
 dissect_swils_fspf_ldrec(tvbuff_t *tvb, proto_tree *tree, int offset)
 {
-    proto_tree_add_string(tree, hf_swils_ldrec_linkid, tvb, offset, 4,
-                          tvb_fc_to_str(tvb, offset+1));
+    proto_tree_add_item(tree, hf_swils_ldrec_linkid, tvb, offset+1, 3, ENC_NA);
     proto_tree_add_item(tree, hf_swils_ldrec_out_pidx, tvb, offset+5, 3, ENC_BIG_ENDIAN);
     proto_tree_add_item(tree, hf_swils_ldrec_nbr_pidx, tvb, offset+9, 3, ENC_BIG_ENDIAN);
     proto_tree_add_item(tree, hf_swils_ldrec_link_type, tvb, offset+12, 1, ENC_BIG_ENDIAN);
@@ -1033,8 +1047,7 @@ dissect_swils_fspf_lsrec(tvbuff_t *tvb, proto_tree *tree, int offset,
                                         ett_fcswils_lsrechdr, NULL, "Link State Record Header");
 
             dissect_swils_fspf_lsrechdr(tvb, lsrechdr_tree, offset);
-            proto_tree_add_text(tree, tvb, offset+26, 2, "Number of Links: %d",
-                                num_ldrec);
+            proto_tree_add_item(tree, hf_swils_lsrec_number_of_links, tvb, offset+26, 2, ENC_BIG_ENDIAN);
             offset += 28;
 
             for (i = 0; i < num_ldrec; i++) {
@@ -1050,7 +1063,7 @@ dissect_swils_fspf_lsrec(tvbuff_t *tvb, proto_tree *tree, int offset,
 }
 
 static void
-dissect_swils_hello(tvbuff_t *tvb, proto_tree *hlo_tree, guint8 isreq _U_)
+dissect_swils_hello(tvbuff_t *tvb, packet_info* pinfo _U_, proto_tree *hlo_tree, guint8 isreq _U_)
 {
     /* Set up structures needed to add the protocol subtree and manage it */
     int offset = 0;
@@ -1067,7 +1080,7 @@ dissect_swils_hello(tvbuff_t *tvb, proto_tree *hlo_tree, guint8 isreq _U_)
 }
 
 static void
-dissect_swils_lsupdate(tvbuff_t *tvb, proto_tree *lsu_tree, guint8 isreq _U_)
+dissect_swils_lsupdate(tvbuff_t *tvb, packet_info* pinfo _U_, proto_tree *lsu_tree, guint8 isreq _U_)
 {
     /* Set up structures needed to add the protocol subtree and manage it */
     int offset = 0;
@@ -1076,13 +1089,10 @@ dissect_swils_lsupdate(tvbuff_t *tvb, proto_tree *lsu_tree, guint8 isreq _U_)
     if (lsu_tree) {
         dissect_swils_fspf_hdr(tvb, lsu_tree, offset);
 
-        proto_tree_add_text(lsu_tree, tvb, offset+23, 1, "Flags : %s",
-                            val_to_str(tvb_get_guint8(tvb, offset+23),
-                                       fc_swils_fspf_lsrflags_val, "0x%x"));
+        proto_tree_add_item(lsu_tree, hf_swils_lsupdate_flags, tvb, offset+23, 1, ENC_BIG_ENDIAN);
         num_lsrec = tvb_get_ntohl(tvb, offset+24);
 
-        proto_tree_add_text(lsu_tree, tvb, offset+24, 4, "Num of LSRs: %d",
-                            num_lsrec);
+        proto_tree_add_item(lsu_tree, hf_swils_lsupdate_num_of_lsrs, tvb, offset+24, 4, ENC_BIG_ENDIAN);
 
         offset = 28;
         dissect_swils_fspf_lsrec(tvb, lsu_tree, offset, num_lsrec);
@@ -1090,7 +1100,7 @@ dissect_swils_lsupdate(tvbuff_t *tvb, proto_tree *lsu_tree, guint8 isreq _U_)
 }
 
 static void
-dissect_swils_lsack(tvbuff_t *tvb, proto_tree *lsa_tree, guint8 isreq _U_)
+dissect_swils_lsack(tvbuff_t *tvb, packet_info* pinfo _U_, proto_tree *lsa_tree, guint8 isreq _U_)
 {
     /* Set up structures needed to add the protocol subtree and manage it */
     int         offset = 0;
@@ -1100,13 +1110,10 @@ dissect_swils_lsack(tvbuff_t *tvb, proto_tree *lsa_tree, guint8 isreq _U_)
     if (lsa_tree) {
         dissect_swils_fspf_hdr(tvb, lsa_tree, offset);
 
-        proto_tree_add_text(lsa_tree, tvb, offset+23, 1, "Flags : %s",
-                            val_to_str(tvb_get_guint8(tvb, offset+23),
-                                       fc_swils_fspf_lsrflags_val, "0x%x"));
+        proto_tree_add_item(lsa_tree, hf_swils_lsack_flags, tvb, offset+23, 1, ENC_BIG_ENDIAN);
         num_lsrechdr = tvb_get_ntohl(tvb, offset+24);
 
-        proto_tree_add_text(lsa_tree, tvb, offset+24, 4, "Num of LSR Headers: %d",
-                            num_lsrechdr);
+        proto_tree_add_item(lsa_tree, hf_swils_lsack_num_of_lsr_headers, tvb, offset+24, 4, ENC_BIG_ENDIAN);
 
         offset = 28;
 
@@ -1121,7 +1128,7 @@ dissect_swils_lsack(tvbuff_t *tvb, proto_tree *lsa_tree, guint8 isreq _U_)
 }
 
 static void
-dissect_swils_rscn(tvbuff_t *tvb, proto_tree *rscn_tree, guint8 isreq)
+dissect_swils_rscn(tvbuff_t *tvb, packet_info* pinfo _U_, proto_tree *rscn_tree, guint8 isreq)
 {
     /* Set up structures needed to add the protocol subtree and manage it */
     int         offset = 0;
@@ -1136,8 +1143,8 @@ dissect_swils_rscn(tvbuff_t *tvb, proto_tree *rscn_tree, guint8 isreq)
                             1, ENC_BIG_ENDIAN);
         proto_tree_add_item(rscn_tree, hf_swils_rscn_addrfmt, tvb, offset+4,
                             1, ENC_BIG_ENDIAN);
-        proto_tree_add_string(rscn_tree, hf_swils_rscn_affectedport, tvb,
-                              offset+5, 3, tvb_fc_to_str(tvb, offset+5));
+        proto_tree_add_item(rscn_tree, hf_swils_rscn_affectedport, tvb,
+                              offset+5, 3, ENC_NA);
         proto_tree_add_item(rscn_tree, hf_swils_rscn_detectfn, tvb,
                             offset+8, 4, ENC_BIG_ENDIAN);
         numrec = tvb_get_ntohl(tvb, offset+12);
@@ -1147,8 +1154,7 @@ dissect_swils_rscn(tvbuff_t *tvb, proto_tree *rscn_tree, guint8 isreq)
             return;
         }
 
-        proto_tree_add_text(rscn_tree, tvb, offset+12, 4, "Num Entries: %d",
-                            numrec);
+        proto_tree_add_item(rscn_tree, hf_swils_rscn_num_entries, tvb, offset+12, 4, ENC_BIG_ENDIAN);
 
         offset = 16;
         for (i = 0; i < numrec; i++) {
@@ -1156,12 +1162,9 @@ dissect_swils_rscn(tvbuff_t *tvb, proto_tree *rscn_tree, guint8 isreq)
                                         ett_fcswils_rscn_dev, NULL, "Device Entry %d", i);
 
             proto_tree_add_item(dev_tree, hf_swils_rscn_portstate, tvb, offset, 1, ENC_BIG_ENDIAN);
-            proto_tree_add_string(dev_tree, hf_swils_rscn_portid, tvb, offset+1, 3,
-                                  tvb_fc_to_str(tvb, offset+1));
-            proto_tree_add_string(dev_tree, hf_swils_rscn_pwwn, tvb, offset+4, 8,
-                                  tvb_fcwwn_to_str(tvb, offset+4));
-            proto_tree_add_string(dev_tree, hf_swils_rscn_nwwn, tvb, offset+12, 8,
-                                  tvb_fcwwn_to_str(tvb, offset+12));
+            proto_tree_add_item(dev_tree, hf_swils_rscn_portid, tvb, offset+1, 3, ENC_NA);
+            proto_tree_add_item(dev_tree, hf_swils_rscn_pwwn, tvb, offset+4, 8, ENC_NA);
+            proto_tree_add_item(dev_tree, hf_swils_rscn_nwwn, tvb, offset+12, 8, ENC_NA);
             offset += 20;
         }
     }
@@ -1182,73 +1185,61 @@ dissect_swils_rscn(tvbuff_t *tvb, proto_tree *rscn_tree, guint8 isreq)
  */
 
 static void
-dissect_swils_zone_mbr(tvbuff_t *tvb, proto_tree *zmbr_tree, int offset)
+dissect_swils_zone_mbr(tvbuff_t *tvb, packet_info* pinfo, proto_tree *zmbr_tree, int offset)
 {
     guint8  mbrtype;
     int     idlen;
-    char    dpbuf[2+8+1];
-    char   *str;
+    proto_item* ti;
 
     mbrtype = tvb_get_guint8(tvb, offset);
-    proto_tree_add_uint(zmbr_tree, hf_swils_zone_mbrtype, tvb,
+    ti = proto_tree_add_uint(zmbr_tree, hf_swils_zone_mbrtype, tvb,
                         offset, 1, mbrtype);
-    proto_tree_add_text(zmbr_tree, tvb, offset+2, 1, "Flags: 0x%x",
-                        tvb_get_guint8(tvb, offset+2));
+    proto_tree_add_item(zmbr_tree, hf_swils_zone_mbrflags, tvb, offset+2, 1, ENC_BIG_ENDIAN);
     idlen = tvb_get_guint8(tvb, offset+3);
-    proto_tree_add_text(zmbr_tree, tvb, offset+3, 1,
-                        "Identifier Length: %u", idlen);
+    proto_tree_add_item(zmbr_tree, hf_swils_zone_mbr_identifier_length, tvb, offset+3, 1, ENC_BIG_ENDIAN);
     switch (mbrtype) {
     case FC_SWILS_ZONEMBR_WWN:
-        proto_tree_add_string(zmbr_tree, hf_swils_zone_mbrid, tvb,
-                              offset+4, 8,
-                              tvb_fcwwn_to_str(tvb, offset+4));
+        proto_tree_add_item(zmbr_tree, hf_swils_zone_mbrid_fcwwn, tvb,
+                              offset+4, 8, ENC_NA);
         break;
     case FC_SWILS_ZONEMBR_DP:
-        g_snprintf(dpbuf, sizeof(dpbuf), "0x%08x", tvb_get_ntohl(tvb, offset+4));
-        proto_tree_add_string(zmbr_tree, hf_swils_zone_mbrid, tvb,
-                              offset+4, 4, dpbuf);
+        proto_tree_add_item(zmbr_tree, hf_swils_zone_mbrid_uint, tvb,
+                              offset+4, 4, ENC_BIG_ENDIAN);
         break;
     case FC_SWILS_ZONEMBR_FCID:
-        proto_tree_add_string(zmbr_tree, hf_swils_zone_mbrid, tvb,
-                              offset+4, 4,
-                              tvb_fc_to_str(tvb, offset+5));
+        proto_tree_add_item(zmbr_tree, hf_swils_zone_mbrid_fc, tvb,
+                              offset+4, 3, ENC_NA);
         break;
     case FC_SWILS_ZONEMBR_ALIAS:
-        str = zonenm_to_str(tvb, offset+4);
         proto_tree_add_string(zmbr_tree, hf_swils_zone_mbrid, tvb,
-                              offset+4, idlen, str);
+                              offset+4, idlen, zonenm_to_str(tvb, offset+4));
         break;
     case FC_SWILS_ZONEMBR_WWN_LUN:
-        proto_tree_add_string(zmbr_tree, hf_swils_zone_mbrid, tvb,
-                              offset+4, 8,
-                              tvb_fcwwn_to_str(tvb, offset+4));
+        proto_tree_add_item(zmbr_tree, hf_swils_zone_mbrid_fcwwn, tvb,
+                              offset+4, 8, ENC_NA);
         proto_tree_add_item(zmbr_tree, hf_swils_zone_mbrid_lun, tvb,
                             offset+12, 8, ENC_NA);
         break;
     case FC_SWILS_ZONEMBR_DP_LUN:
-        g_snprintf(dpbuf, sizeof(dpbuf), "0x%08x", tvb_get_ntohl(tvb, offset+4));
-        proto_tree_add_string(zmbr_tree, hf_swils_zone_mbrid, tvb,
-                              offset+4, 4, dpbuf);
+        proto_tree_add_item(zmbr_tree, hf_swils_zone_mbrid_uint, tvb,
+                              offset+4, 4, ENC_BIG_ENDIAN);
         proto_tree_add_item(zmbr_tree, hf_swils_zone_mbrid_lun, tvb,
                             offset+8, 8, ENC_NA);
         break;
     case FC_SWILS_ZONEMBR_FCID_LUN:
-        proto_tree_add_string(zmbr_tree, hf_swils_zone_mbrid, tvb,
-                              offset+4, 4,
-                              tvb_fc_to_str(tvb, offset+5));
+        proto_tree_add_item(zmbr_tree, hf_swils_zone_mbrid_fc, tvb,
+                              offset+4, 3, ENC_NA);
         proto_tree_add_item(zmbr_tree, hf_swils_zone_mbrid_lun, tvb,
                             offset+8, 8, ENC_NA);
         break;
     default:
-        proto_tree_add_string(zmbr_tree, hf_swils_zone_mbrid, tvb,
-                              offset+4, idlen,
-                              "Unknown member type format");
+        expert_add_info(pinfo, ti, &ei_swils_zone_mbrid);
 
     }
 }
 
 static void
-dissect_swils_zone_obj(tvbuff_t *tvb, proto_tree *zobj_tree, int offset)
+dissect_swils_zone_obj(tvbuff_t *tvb, packet_info* pinfo, proto_tree *zobj_tree, int offset)
 {
     proto_tree *zmbr_tree;
     int         mbrlen, numrec, i, objtype;
@@ -1265,28 +1256,26 @@ dissect_swils_zone_obj(tvbuff_t *tvb, proto_tree *zobj_tree, int offset)
                           offset+4, ZONENAME_LEN(tvb, offset+4), str);
 
     numrec = tvb_get_ntohl(tvb, offset+4+ZONENAME_LEN(tvb, offset+4));
-    proto_tree_add_text(zobj_tree, tvb,
-                        offset+4+ZONENAME_LEN(tvb, offset+4), 4,
-                        "Number of Zone Members: %d", numrec);
+    proto_tree_add_item(zobj_tree, hf_swils_zone_num_members, tvb, offset+4+ZONENAME_LEN(tvb,offset+4), 4, ENC_BIG_ENDIAN);
 
     offset += 8 + ZONENAME_LEN(tvb, offset+4);
     for (i = 0; i < numrec; i++) {
         if (objtype == FC_SWILS_ZONEOBJ_ZONESET) {
-            dissect_swils_zone_obj(tvb, zobj_tree, offset);
+            dissect_swils_zone_obj(tvb, pinfo, zobj_tree, offset);
             offset += get_zoneobj_len(tvb, offset);
         }
         else {
             mbrlen = 4 + tvb_get_guint8(tvb, offset+3);
             zmbr_tree = proto_tree_add_subtree_format(zobj_tree, tvb, offset, mbrlen,
                                         ett_fcswils_zonembr, NULL, "Zone Member %d", i);
-            dissect_swils_zone_mbr(tvb, zmbr_tree, offset);
+            dissect_swils_zone_mbr(tvb, pinfo, zmbr_tree, offset);
             offset += mbrlen;
         }
     }
 }
 
 static void
-dissect_swils_mergereq(tvbuff_t *tvb, proto_tree *mr_tree, guint8 isreq)
+dissect_swils_mergereq(tvbuff_t *tvb, packet_info* pinfo, proto_tree *mr_tree, guint8 isreq)
 {
     /* Set up structures needed to add the protocol subtree and manage it */
     int         offset = 0;
@@ -1294,12 +1283,10 @@ dissect_swils_mergereq(tvbuff_t *tvb, proto_tree *mr_tree, guint8 isreq)
     int         numrec, i, zonesetlen, objlistlen, objlen;
     char       *str;
 
-    if (mr_tree) {
         if (isreq) {
             /* zonesetlen is the size of the zoneset including the zone name */
             zonesetlen = tvb_get_ntohs(tvb, offset+2);
-            proto_tree_add_text(mr_tree, tvb, offset+2, 2,
-                                "Active ZoneSet Length: %u", zonesetlen);
+            proto_tree_add_item(mr_tree, hf_swils_zone_active_zoneset_length, tvb, offset+2, 2, ENC_BIG_ENDIAN);
 
             if (zonesetlen) {
                 str = zonenm_to_str(tvb, offset+4);
@@ -1316,15 +1303,14 @@ dissect_swils_mergereq(tvbuff_t *tvb, proto_tree *mr_tree, guint8 isreq)
                 zobjlist_tree = proto_tree_add_subtree(mr_tree, tvb, offset, objlistlen,
                                             ett_fcswils_zoneobjlist, NULL, "Active Zone Set");
 
-                proto_tree_add_text(zobjlist_tree, tvb, offset, 4,
-                                    "Number of zoning objects: %d", numrec);
+                proto_tree_add_item(zobjlist_tree, hf_swils_zone_num_zoning_objects, tvb, offset, 4, ENC_BIG_ENDIAN);
 
                 offset += 4;
                 for (i = 0; i < numrec; i++) {
                     objlen = get_zoneobj_len(tvb, offset);
                     zobj_tree = proto_tree_add_subtree_format(zobjlist_tree, tvb, offset+4, objlen,
                                                 ett_fcswils_zoneobj, NULL, "Zone Object %d", i);
-                    dissect_swils_zone_obj(tvb, zobj_tree, offset);
+                    dissect_swils_zone_obj(tvb, pinfo, zobj_tree, offset);
                     offset += objlen;
                 }
             }
@@ -1333,8 +1319,7 @@ dissect_swils_mergereq(tvbuff_t *tvb, proto_tree *mr_tree, guint8 isreq)
             }
 
             zonesetlen = tvb_get_ntohl(tvb, offset);
-            proto_tree_add_text(mr_tree, tvb, offset, 4,
-                                "Full Zone Set Length: %d", zonesetlen);
+            proto_tree_add_item(mr_tree, hf_swils_zone_full_zone_set_length, tvb, offset, 4, ENC_BIG_ENDIAN);
 
             if (zonesetlen) {
                 objlistlen = zonesetlen;
@@ -1345,14 +1330,13 @@ dissect_swils_mergereq(tvbuff_t *tvb, proto_tree *mr_tree, guint8 isreq)
                 zobjlist_tree = proto_tree_add_subtree(mr_tree, tvb, offset, objlistlen,
                                             ett_fcswils_zoneobjlist, NULL, "Full Zone Set");
 
-                proto_tree_add_text(zobjlist_tree, tvb, offset, 4,
-                                    "Number of zoning objects: %d", numrec);
+                proto_tree_add_item(zobjlist_tree, hf_swils_zone_num_zoning_objects, tvb, offset, 4, ENC_BIG_ENDIAN);
                 offset += 4;
                 for (i = 0; i < numrec; i++) {
                     objlen = get_zoneobj_len(tvb, offset);
                     zobj_tree = proto_tree_add_subtree_format(zobjlist_tree, tvb, offset,
                                                 objlen, ett_fcswils_zoneobj, NULL, "Zone Object %d", i);
-                    dissect_swils_zone_obj(tvb, zobj_tree, offset);
+                    dissect_swils_zone_obj(tvb, pinfo, zobj_tree, offset);
                     offset += objlen;
                 }
             }
@@ -1362,15 +1346,12 @@ dissect_swils_mergereq(tvbuff_t *tvb, proto_tree *mr_tree, guint8 isreq)
                                 offset+5, 1, ENC_BIG_ENDIAN);
             proto_tree_add_item(mr_tree, hf_swils_zone_reason, tvb,
                                 offset+6, 1, ENC_BIG_ENDIAN);
-            proto_tree_add_text(mr_tree, tvb, offset+7, 1,
-                                "Vendor Unique: 0x%x",
-                                tvb_get_guint8(tvb, offset+7));
+            proto_tree_add_item(mr_tree, hf_swils_zone_vendor_unique, tvb, offset+7, 1, ENC_BIG_ENDIAN);
         }
-    }
 }
 
 static void
-dissect_swils_aca(tvbuff_t *tvb, proto_tree *aca_tree, guint8 isreq)
+dissect_swils_aca(tvbuff_t *tvb, packet_info* pinfo _U_, proto_tree *aca_tree, guint8 isreq)
 {
     /* Set up structures needed to add the protocol subtree and manage it */
     int offset = 0;
@@ -1379,8 +1360,7 @@ dissect_swils_aca(tvbuff_t *tvb, proto_tree *aca_tree, guint8 isreq)
     if (aca_tree) {
         if (isreq) {
             plen = tvb_get_ntohs(tvb, offset+2);
-            proto_tree_add_text(aca_tree, tvb, offset+2, 2,
-                                "Domain ID List Length: %d", plen);
+            proto_tree_add_item(aca_tree, hf_swils_domain_id_list_length, tvb, offset+2, 2, ENC_BIG_ENDIAN);
             numrec = plen/4;
             offset = 4;
 
@@ -1398,15 +1378,13 @@ dissect_swils_aca(tvbuff_t *tvb, proto_tree *aca_tree, guint8 isreq)
                                 offset+5, 1, ENC_BIG_ENDIAN);
             proto_tree_add_item(aca_tree, hf_swils_zone_reason, tvb,
                                 offset+6, 1, ENC_BIG_ENDIAN);
-            proto_tree_add_text(aca_tree, tvb, offset+7, 1,
-                                "Vendor Unique: 0x%x",
-                                tvb_get_guint8(tvb, offset+7));
+            proto_tree_add_item(aca_tree, hf_swils_zone_vendor_unique, tvb, offset+7, 1, ENC_BIG_ENDIAN);
         }
     }
 }
 
 static void
-dissect_swils_rca(tvbuff_t *tvb, proto_tree *rca_tree, guint8 isreq)
+dissect_swils_rca(tvbuff_t *tvb, packet_info* pinfo _U_, proto_tree *rca_tree, guint8 isreq)
 {
     /* Set up structures needed to add the protocol subtree and manage it */
     int offset = 0;
@@ -1417,15 +1395,13 @@ dissect_swils_rca(tvbuff_t *tvb, proto_tree *rca_tree, guint8 isreq)
                                 offset+5, 1, ENC_BIG_ENDIAN);
             proto_tree_add_item(rca_tree, hf_swils_zone_reason, tvb,
                                 offset+6, 1, ENC_BIG_ENDIAN);
-            proto_tree_add_text(rca_tree, tvb, offset+7, 1,
-                                "Vendor Unique: 0x%x",
-                                tvb_get_guint8(tvb, offset+7));
+            proto_tree_add_item(rca_tree, hf_swils_zone_vendor_unique, tvb, offset+7, 1, ENC_BIG_ENDIAN);
         }
     }
 }
 
 static void
-dissect_swils_sfc(tvbuff_t *tvb, proto_tree *sfc_tree, guint8 isreq)
+dissect_swils_sfc(tvbuff_t *tvb, packet_info* pinfo _U_, proto_tree *sfc_tree, guint8 isreq)
 {
     /* Set up structures needed to add the protocol subtree and manage it */
     int         offset = 0;
@@ -1433,13 +1409,11 @@ dissect_swils_sfc(tvbuff_t *tvb, proto_tree *sfc_tree, guint8 isreq)
     int         numrec, i, zonesetlen, objlistlen, objlen;
     char       *str;
 
-    if (sfc_tree) {
         if (isreq) {
             proto_tree_add_item(sfc_tree, hf_swils_sfc_opcode, tvb, offset+1, 1, ENC_BIG_ENDIAN);
 
             zonesetlen = tvb_get_ntohs(tvb, offset+2);
-            proto_tree_add_text(sfc_tree, tvb, offset+2, 2,
-                                "ZoneSet Length: %d", zonesetlen);
+            proto_tree_add_item(sfc_tree, hf_swils_sfc_zoneset_length, tvb, offset+2, 2, ENC_BIG_ENDIAN);
 
             if (zonesetlen) {
                 str = zonenm_to_str(tvb, offset+4);
@@ -1456,15 +1430,14 @@ dissect_swils_sfc(tvbuff_t *tvb, proto_tree *sfc_tree, guint8 isreq)
                 zobjlist_tree = proto_tree_add_subtree(sfc_tree, tvb, offset, objlistlen,
                                             ett_fcswils_zoneobjlist, NULL, "Zone Set");
 
-                proto_tree_add_text(zobjlist_tree, tvb, offset, 4,
-                                    "Number of zoning objects: %d", numrec);
+                proto_tree_add_item(zobjlist_tree, hf_swils_zone_num_zoning_objects, tvb, offset, 4, ENC_BIG_ENDIAN);
 
                 offset += 4;
                 for (i = 0; i < numrec; i++) {
                     objlen = get_zoneobj_len(tvb, offset);
                     zobj_tree = proto_tree_add_subtree_format(zobjlist_tree, tvb, offset, objlen,
                                                 ett_fcswils_zoneobj, NULL, "Zone Object %d", i);
-                    dissect_swils_zone_obj(tvb, zobj_tree, offset);
+                    dissect_swils_zone_obj(tvb, pinfo, zobj_tree, offset);
                     offset += objlen;
                 }
             }
@@ -1473,8 +1446,7 @@ dissect_swils_sfc(tvbuff_t *tvb, proto_tree *sfc_tree, guint8 isreq)
             }
 
             zonesetlen = tvb_get_ntohl(tvb, offset);
-            proto_tree_add_text(sfc_tree, tvb, offset, 4,
-                                "Full Zone Set Length: %d", zonesetlen);
+            proto_tree_add_item(sfc_tree, hf_swils_zone_full_zone_set_length, tvb, offset, 4, ENC_BIG_ENDIAN);
 
             if (zonesetlen) {
                 objlistlen = zonesetlen;
@@ -1485,14 +1457,13 @@ dissect_swils_sfc(tvbuff_t *tvb, proto_tree *sfc_tree, guint8 isreq)
                 zobjlist_tree = proto_tree_add_subtree(sfc_tree, tvb, offset, objlistlen,
                                             ett_fcswils_zoneobjlist, NULL, "Full Zone Set");
 
-                proto_tree_add_text(zobjlist_tree, tvb, offset, 4,
-                                    "Number of zoning objects: %d", numrec);
+                proto_tree_add_item(zobjlist_tree, hf_swils_zone_num_zoning_objects, tvb, offset, 4, ENC_BIG_ENDIAN);
                 offset += 4;
                 for (i = 0; i < numrec; i++) {
                     objlen = get_zoneobj_len(tvb, offset);
                     zobj_tree = proto_tree_add_subtree_format(zobjlist_tree, tvb, offset, objlen,
                                                 ett_fcswils_zoneobj, NULL, "Zone Object %d", i);
-                    dissect_swils_zone_obj(tvb, zobj_tree, offset);
+                    dissect_swils_zone_obj(tvb, pinfo, zobj_tree, offset);
                     offset += objlen;
                 }
             }
@@ -1502,15 +1473,12 @@ dissect_swils_sfc(tvbuff_t *tvb, proto_tree *sfc_tree, guint8 isreq)
                                 offset+5, 1, ENC_BIG_ENDIAN);
             proto_tree_add_item(sfc_tree, hf_swils_zone_reason, tvb,
                                 offset+6, 1, ENC_BIG_ENDIAN);
-            proto_tree_add_text(sfc_tree, tvb, offset+7, 1,
-                                "Vendor Unique: 0x%x",
-                                tvb_get_guint8(tvb, offset+7));
+            proto_tree_add_item(sfc_tree, hf_swils_zone_vendor_unique, tvb, offset+7, 1, ENC_BIG_ENDIAN);
         }
-    }
 }
 
 static void
-dissect_swils_ufc(tvbuff_t *tvb, proto_tree *ufc_tree, guint8 isreq)
+dissect_swils_ufc(tvbuff_t *tvb, packet_info* pinfo _U_, proto_tree *ufc_tree, guint8 isreq)
 {
     /* Set up structures needed to add the protocol subtree and manage it */
     int offset = 0;
@@ -1521,15 +1489,13 @@ dissect_swils_ufc(tvbuff_t *tvb, proto_tree *ufc_tree, guint8 isreq)
                                 offset+5, 1, ENC_BIG_ENDIAN);
             proto_tree_add_item(ufc_tree, hf_swils_zone_reason, tvb,
                                 offset+6, 1, ENC_BIG_ENDIAN);
-            proto_tree_add_text(ufc_tree, tvb, offset+7, 1,
-                                "Vendor Unique: 0x%x",
-                                tvb_get_guint8(tvb, offset+7));
+            proto_tree_add_item(ufc_tree, hf_swils_zone_vendor_unique, tvb, offset+7, 1, ENC_BIG_ENDIAN);
         }
     }
 }
 
 static void
-dissect_swils_esc(tvbuff_t *tvb, proto_tree *esc_tree, guint8 isreq)
+dissect_swils_esc(tvbuff_t *tvb, packet_info* pinfo _U_, proto_tree *esc_tree, guint8 isreq)
 {
     /* Set up structures needed to add the protocol subtree and manage it */
     int         offset = 0;
@@ -1539,8 +1505,7 @@ dissect_swils_esc(tvbuff_t *tvb, proto_tree *esc_tree, guint8 isreq)
     if (esc_tree) {
         if (isreq) {
             plen = tvb_get_ntohs(tvb, offset+2);
-            proto_tree_add_text(esc_tree, tvb, offset+2, 2,
-                                "Payload Length: %d", plen);
+            proto_tree_add_item(esc_tree, hf_swils_esc_payload_length, tvb, offset+2, 2, ENC_BIG_ENDIAN);
             proto_tree_add_item(esc_tree, hf_swils_esc_swvendorid, tvb,
                                 offset+4, 8, ENC_ASCII|ENC_NA);
             numrec = (plen - 12)/12;
@@ -1571,7 +1536,7 @@ dissect_swils_esc(tvbuff_t *tvb, proto_tree *esc_tree, guint8 isreq)
 }
 
 static void
-dissect_swils_drlir(tvbuff_t *tvb _U_, proto_tree *drlir_tree _U_,
+dissect_swils_drlir(tvbuff_t *tvb _U_, packet_info* pinfo _U_, proto_tree *drlir_tree _U_,
                     guint8 isreq _U_)
 {
     /* Set up structures needed to add the protocol subtree and manage it */
@@ -1579,7 +1544,7 @@ dissect_swils_drlir(tvbuff_t *tvb _U_, proto_tree *drlir_tree _U_,
 }
 
 static void
-dissect_swils_swrjt(tvbuff_t *tvb, proto_tree *swrjt_tree, guint8 isreq _U_)
+dissect_swils_swrjt(tvbuff_t *tvb, packet_info* pinfo _U_, proto_tree *swrjt_tree, guint8 isreq _U_)
 {
     /* Set up structures needed to add the protocol subtree and manage it */
     int offset = 0;
@@ -1593,7 +1558,7 @@ dissect_swils_swrjt(tvbuff_t *tvb, proto_tree *swrjt_tree, guint8 isreq _U_)
 }
 
 static void
-dissect_swils_ess(tvbuff_t *tvb, proto_tree *ess_tree, guint8 isreq _U_)
+dissect_swils_ess(tvbuff_t *tvb, packet_info* pinfo _U_, proto_tree *ess_tree, guint8 isreq _U_)
 {
     int         offset      = 0;
     gint16      numcapobj   = 0;
@@ -1631,7 +1596,7 @@ dissect_swils_ess(tvbuff_t *tvb, proto_tree *ess_tree, guint8 isreq _U_)
 }
 
 static void
-dissect_swils_mrra(tvbuff_t *tvb, proto_tree *tree, guint8 isreq)
+dissect_swils_mrra(tvbuff_t *tvb, packet_info* pinfo _U_, proto_tree *tree, guint8 isreq)
 {
 
     int offset = 0;
@@ -1787,8 +1752,7 @@ dissect_fcswils(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void* data)
         if (!conversation) {
             if (tree && (opcode == FC_SWILS_SWACC)) {
                 /* No record of what this accept is for. Can't decode */
-                proto_tree_add_text(swils_tree, tvb, 0, tvb_length(tvb),
-                                    "No record of Exchg. Unable to decode SW_ACC");
+                proto_tree_add_expert_format(swils_tree, pinfo, &ei_swils_no_exchange, tvb, 0, -1, "No record of Exchg. Unable to decode SW_ACC");
                 return 0;
             }
         }
@@ -1807,8 +1771,7 @@ dissect_fcswils(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void* data)
             if (tree) {
                 if ((cdata == NULL) && (opcode != FC_SWILS_SWRJT)) {
                     /* No record of what this accept is for. Can't decode */
-                    proto_tree_add_text(swils_tree, tvb, 0, tvb_length(tvb),
-                                        "No record of SW_ILS Req. Unable to decode SW_ACC");
+                    proto_tree_add_expert_format(swils_tree, pinfo, &ei_swils_no_exchange, tvb, 0, -1, "No record of SW_ILS Req. Unable to decode SW_ACC");
                     return 0;
                 }
             }
@@ -1828,12 +1791,10 @@ dissect_fcswils(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void* data)
                         val_to_str(opcode, fc_swils_opcode_key_val, "0x%x"));
     }
 
-    if (tree) {
-        proto_tree_add_item(swils_tree, hf_swils_opcode, tvb, offset, 1, ENC_BIG_ENDIAN);
-    }
+    proto_tree_add_item(swils_tree, hf_swils_opcode, tvb, offset, 1, ENC_BIG_ENDIAN);
 
     if ((opcode < FC_SWILS_MAXCODE) && fcswils_func_table[opcode].func) {
-        fcswils_func_table[opcode].func(tvb, swils_tree, isreq);
+        fcswils_func_table[opcode].func(tvb, pinfo, swils_tree, isreq);
     } else if (opcode == FC_SWILS_AUTH_ILS) {
         /* This is treated differently */
         if (isreq && fcsp_handle)
@@ -1844,7 +1805,7 @@ dissect_fcswils(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void* data)
         call_dissector(data_handle, next_tvb, pinfo, tree);
     }
 
-    return tvb_length(tvb);
+    return tvb_captured_length(tvb);
 }
 
 /* Register the protocol with Wireshark */
@@ -1880,12 +1841,12 @@ proto_register_fcswils(void)
 
         { &hf_swils_elp_req_epn,
           {"Req Eport Name", "swils.elp.reqepn",
-           FT_STRING, BASE_NONE, NULL, 0x0,
+           FT_FCWWN, BASE_NONE, NULL, 0x0,
            NULL, HFILL}},
 
         { &hf_swils_elp_req_esn,
           {"Req Switch Name", "swils.elp.reqesn",
-           FT_STRING, BASE_NONE, NULL, 0x0,
+           FT_FCWWN, BASE_NONE, NULL, 0x0,
            NULL, HFILL}},
 
         { &hf_swils_elp_clsf_svcp,
@@ -1990,7 +1951,7 @@ proto_register_fcswils(void)
 
         { &hf_swils_efp_switch_name,
           {"Switch Name", "swils.efp.sname",
-           FT_STRING, BASE_NONE, NULL, 0x0,
+           FT_FCWWN, BASE_NONE, NULL, 0x0,
            NULL, HFILL}},
 
         { &hf_swils_efp_mcast_grpno,
@@ -2022,12 +1983,12 @@ proto_register_fcswils(void)
 
         { &hf_swils_efp_pswitch_name,
           {"Principal Switch Name", "swils.efp.psname",
-           FT_STRING, BASE_NONE, NULL, 0x0,
+           FT_FCWWN, BASE_NONE, NULL, 0x0,
            NULL, HFILL}},
 
         { &hf_swils_dia_switch_name,
           {"Switch Name", "swils.dia.sname",
-           FT_STRING, BASE_NONE, NULL, 0x0,
+           FT_FCWWN, BASE_NONE, NULL, 0x0,
            NULL, HFILL}},
 
         { &hf_swils_rdi_payload_len,
@@ -2037,7 +1998,7 @@ proto_register_fcswils(void)
 
         { &hf_swils_rdi_req_sname,
           {"Req Switch Name", "swils.rdi.reqsn",
-           FT_STRING, BASE_NONE, NULL, 0x0,
+           FT_FCWWN, BASE_NONE, NULL, 0x0,
            NULL, HFILL}},
 
 #if 0
@@ -2119,7 +2080,7 @@ proto_register_fcswils(void)
 
         { &hf_swils_ldrec_linkid,
           {"Link ID", "swils.ldr.linkid",
-           FT_STRING, BASE_NONE, NULL, 0x0,
+           FT_BYTES, SEP_DOT, NULL, 0x0,
            NULL, HFILL}},
 
         { &hf_swils_ldrec_out_pidx,
@@ -2154,7 +2115,7 @@ proto_register_fcswils(void)
 
         { &hf_swils_rscn_affectedport,
           {"Affected Port ID", "swils.rscn.affectedport",
-           FT_STRING, BASE_NONE, NULL, 0x0,
+           FT_BYTES, SEP_DOT, NULL, 0x0,
            NULL, HFILL}},
 
         { &hf_swils_rscn_detectfn,
@@ -2169,17 +2130,17 @@ proto_register_fcswils(void)
 
         { &hf_swils_rscn_portid,
           {"Port Id", "swils.rscn.portid",
-           FT_STRING, BASE_NONE, NULL, 0x0,
+           FT_BYTES, SEP_DOT, NULL, 0x0,
            NULL, HFILL}},
 
         { &hf_swils_rscn_pwwn,
           {"Port WWN", "swils.rscn.pwwn",
-           FT_STRING, BASE_NONE, NULL, 0x0,
+           FT_FCWWN, BASE_NONE, NULL, 0x0,
            NULL, HFILL}},
 
         { &hf_swils_rscn_nwwn,
           {"Node WWN", "swils.rscn.nwwn",
-           FT_STRING, BASE_NONE, NULL, 0x0,
+           FT_FCWWN, BASE_NONE, NULL, 0x0,
            NULL, HFILL}},
 
         { &hf_swils_esc_swvendorid,
@@ -2227,6 +2188,21 @@ proto_register_fcswils(void)
            FT_STRING, BASE_NONE, NULL, 0x0,
            NULL, HFILL}},
 
+        { &hf_swils_zone_mbrid_fcwwn,
+          {"Member Identifier", "swils.zone.mbrid.fcwwn",
+           FT_FCWWN, BASE_NONE, NULL, 0x0,
+           NULL, HFILL}},
+
+        { &hf_swils_zone_mbrid_fc,
+          {"Member Identifier", "swils.zone.mbrid.fc",
+           FT_BYTES, SEP_DOT, NULL, 0x0,
+           NULL, HFILL}},
+
+        { &hf_swils_zone_mbrid_uint,
+          {"Member Identifier", "swils.zone.mbrid.uint",
+           FT_UINT32, BASE_HEX, NULL, 0x0,
+           NULL, HFILL}},
+
         { &hf_swils_zone_status,
           {"Zone Command Status", "swils.zone.status",
            FT_UINT8, BASE_HEX, VALS(fc_swils_mr_rsp_val), 0x0,
@@ -2482,6 +2458,29 @@ proto_register_fcswils(void)
            FT_UINT32, BASE_DEC, NULL, 0x0,
            NULL, HFILL}},
 
+      /* Generated from convert_proto_tree_add_text.pl */
+      { &hf_swils_requested_domain_id, { "Requested Domain ID", "swils.requested_domain_id", FT_UINT8, BASE_DEC, NULL, 0x0, NULL, HFILL }},
+      { &hf_swils_granted_domain_id, { "Granted Domain ID", "swils.granted_domain_id", FT_UINT8, BASE_DEC, NULL, 0x0, NULL, HFILL }},
+      { &hf_swils_lsrh_lsr_age, { "LSR Age", "swils.lsr.age", FT_UINT16, BASE_DEC, NULL, 0x0, NULL, HFILL }},
+      { &hf_swils_lsrh_options, { "Options", "swils.lsr.options", FT_UINT32, BASE_HEX, NULL, 0x0, NULL, HFILL }},
+      { &hf_swils_lsrh_checksum, { "Checksum", "swils.lsr.checksum", FT_UINT16, BASE_HEX, NULL, 0x0, NULL, HFILL }},
+      { &hf_swils_lsrh_lsr_length, { "LSR Length", "swils.lsr.length", FT_UINT16, BASE_DEC, NULL, 0x0, NULL, HFILL }},
+      { &hf_swils_lsrec_number_of_links, { "Number of Links", "swils.lsr.number_of_links", FT_UINT16, BASE_DEC, NULL, 0x0, NULL, HFILL }},
+      { &hf_swils_lsupdate_flags, { "Flags", "swils.lsupdate.flags", FT_UINT8, BASE_HEX, VALS(fc_swils_fspf_lsrflags_val), 0x0, NULL, HFILL }},
+      { &hf_swils_lsupdate_num_of_lsrs, { "Num of LSRs", "swils.lsupdate.num_of_lsrs", FT_UINT32, BASE_DEC, NULL, 0x0, NULL, HFILL }},
+      { &hf_swils_lsack_flags, { "Flags", "swils.lsack.flags", FT_UINT8, BASE_HEX, VALS(fc_swils_fspf_lsrflags_val), 0x0, NULL, HFILL }},
+      { &hf_swils_lsack_num_of_lsr_headers, { "Num of LSR Headers", "swils.lsack.num_of_lsr_headers", FT_UINT32, BASE_DEC, NULL, 0x0, NULL, HFILL }},
+      { &hf_swils_rscn_num_entries, { "Num Entries", "swils.rscn.num_entries", FT_UINT32, BASE_DEC, NULL, 0x0, NULL, HFILL }},
+      { &hf_swils_zone_mbrflags, { "Flags", "swils.zone.flags", FT_UINT8, BASE_HEX, NULL, 0x0, NULL, HFILL }},
+      { &hf_swils_zone_mbr_identifier_length, { "Identifier Length", "swils.zone.identifier_length", FT_UINT8, BASE_DEC, NULL, 0x0, NULL, HFILL }},
+      { &hf_swils_zone_num_members, { "4", "swils.zone.num_members", FT_UINT32, BASE_DEC, NULL, 0x0, NULL, HFILL }},
+      { &hf_swils_zone_active_zoneset_length, { "Active ZoneSet Length", "swils.zone.active_zoneset_length", FT_UINT16, BASE_DEC, NULL, 0x0, NULL, HFILL }},
+      { &hf_swils_zone_num_zoning_objects, { "Number of zoning objects", "swils.zone.num_zoning_objects", FT_UINT32, BASE_DEC, NULL, 0x0, NULL, HFILL }},
+      { &hf_swils_zone_full_zone_set_length, { "Full Zone Set Length", "swils.zone.full_zone_set_length", FT_UINT32, BASE_DEC, NULL, 0x0, NULL, HFILL }},
+      { &hf_swils_zone_vendor_unique, { "Vendor Unique", "swils.zone.vendor_unique", FT_UINT8, BASE_HEX, NULL, 0x0, NULL, HFILL }},
+      { &hf_swils_domain_id_list_length, { "Domain ID List Length", "swils.aca.domain_id_list_length", FT_UINT16, BASE_DEC, NULL, 0x0, NULL, HFILL }},
+      { &hf_swils_sfc_zoneset_length, { "ZoneSet Length", "swils.sfc.zoneset_length", FT_UINT16, BASE_DEC, NULL, 0x0, NULL, HFILL }},
+      { &hf_swils_esc_payload_length, { "Payload Length", "swils.esc.payload_length", FT_UINT16, BASE_DEC, NULL, 0x0, NULL, HFILL }},
     };
 
     static gint *ett[] = {
@@ -2519,11 +2518,22 @@ proto_register_fcswils(void)
         &ett_fcswils_capinfo
     };
 
+    static ei_register_info ei[] = {
+        { &ei_swils_efp_record_len, { "swils.efp.recordlen.zero", PI_UNDECODED, PI_NOTE, "Record length is zero", EXPFILL }},
+        { &ei_swils_no_exchange, { "swils.no_exchange", PI_UNDECODED, PI_WARN, "No record of Exchg. Unable to decode", EXPFILL }},
+        { &ei_swils_zone_mbrid, { "swils.zone.mbrid.unknown_type", PI_PROTOCOL, PI_WARN, "Unknown member type format", EXPFILL }},
+    };
+
+    expert_module_t* expert_fcswils;
+
     proto_fcswils = proto_register_protocol("Fibre Channel SW_ILS", "FC-SWILS", "swils");
 
     proto_register_field_array(proto_fcswils, hf, array_length(hf));
     proto_register_subtree_array(ett, array_length(ett));
+    expert_fcswils = expert_register_protocol(proto_fcswils);
+    expert_register_field_array(expert_fcswils, ei, array_length(ei));
     register_init_routine(&fcswils_init_protocol);
+    register_cleanup_routine(&fcswils_cleanup_protocol);
 }
 
 void
@@ -2537,3 +2547,16 @@ proto_reg_handoff_fcswils(void)
     data_handle = find_dissector("data");
     fcsp_handle = find_dissector("fcsp");
 }
+
+/*
+ * Editor modelines  -  http://www.wireshark.org/tools/modelines.html
+ *
+ * Local variables:
+ * c-basic-offset: 4
+ * tab-width: 8
+ * indent-tabs-mode: nil
+ * End:
+ *
+ * vi: set shiftwidth=4 tabstop=8 expandtab:
+ * :indentSize=4:tabSize=8:noTabs=true:
+ */