Fix various typos and spelling errors.
[obnox/wireshark/wip.git] / epan / dissectors / packet-smb.c
index 2f277272919bfa4652d921b31a611dda0e5b4da1..f106e5565df49fd4c3942e801068f6ab3d24da1a 100644 (file)
@@ -30,8 +30,6 @@
 # include "config.h"
 #endif
 
-#include <stdio.h>
-
 #include <time.h>
 #include <string.h>
 #include <glib.h>
@@ -367,8 +365,13 @@ static int hf_smb_lanman = -1;
 static int hf_smb_setup_action_guest = -1;
 static int hf_smb_fs = -1;
 static int hf_smb_connect_flags_dtid = -1;
+static int hf_smb_connect_flags_ext_sig = -1;
+static int hf_smb_connect_flags_ext_resp = -1;
 static int hf_smb_connect_support_search = -1;
 static int hf_smb_connect_support_in_dfs = -1;
+static int hf_smb_connect_support_csc_mask_vals = -1;
+static int hf_smb_connect_support_uniquefilename = -1;
+static int hf_smb_connect_support_extended_signature = -1;
 static int hf_smb_max_setup_count = -1;
 static int hf_smb_total_param_count = -1;
 static int hf_smb_total_data_count = -1;
@@ -642,6 +645,7 @@ static int hf_smb_segment_overlap_conflict = -1;
 static int hf_smb_segment_multiple_tails = -1;
 static int hf_smb_segment_too_long_fragment = -1;
 static int hf_smb_segment_error = -1;
+static int hf_smb_reassembled_length = -1;
 static int hf_smb_pipe_write_len = -1;
 static int hf_smb_unix_major_version = -1;
 static int hf_smb_unix_minor_version = -1;
@@ -766,6 +770,7 @@ static gint ett_smb_posic_ace = -1;
 static gint ett_smb_posix_ace_perms = -1;
 
 static int smb_tap = -1;
+static int smb_eo_tap = -1;
 
 static dissector_handle_t gssapi_handle;
 static dissector_handle_t ntlmssp_handle;
@@ -782,11 +787,11 @@ static const fragment_items smb_frag_items = {
        &hf_smb_segment_too_long_fragment,
        &hf_smb_segment_error,
        NULL,
-
+       &hf_smb_reassembled_length,
        "segments"
 };
 
-static proto_tree *top_tree=NULL;     /* ugly */
+static proto_tree *top_tree_global=NULL;     /* ugly */
 
 static const char *decode_smb_name(guint8);
 static int dissect_smb_command(tvbuff_t *tvb, packet_info *pinfo, int offset, proto_tree *smb_tree, guint8 cmd, gboolean first_pdu);
@@ -882,9 +887,17 @@ static int dissect_smb_command(tvbuff_t *tvb, packet_info *pinfo, int offset, pr
        offset += len;                  \
        *bcp -= len;
 
-
+gboolean sid_display_hex = FALSE;
 gboolean sid_name_snooping = FALSE;
 
+/* Compare funtion to maintain the GSL_fid_info ordered
+   Order criteria: packet where the fid was opened */
+static gint
+fid_cmp(smb_fid_info_t *fida, smb_fid_info_t *fidb)
+{
+        return (fida->opened_in - fidb->opened_in);
+}
+
 /* XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
    These are needed by the reassembly of SMB Transaction payload and DCERPC over SMB
    XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX */
@@ -1577,75 +1590,47 @@ static const true_false_string tfs_file_attribute_encrypted = {
 };
 
 /*
- * In some places in the CIFS_TR_1p00.pdf, from SNIA, file attributes are
- * listed as USHORT, and seem to be in packets in the wild, while in other
- * places they are listed as ULONG, and also seem to be.
- *
- * So, I (Richard Sharpe), added a parameter to allow us to specify how many
- * bytes to consume.
+ * Dissects an SMB_FILE_ATTRIBUTES, to use the term given to it by
+ * section 2.2.1.2.4 of [MS-CIFS], in cases where it's just file attributes,
+ * not search attributes.
  */
-
-int
-dissect_file_attributes(tvbuff_t *tvb, proto_tree *parent_tree, int offset,
-                       int bytes)
+static int
+dissect_file_attributes(tvbuff_t *tvb, proto_tree *parent_tree, int offset)
 {
        guint16 mask;
        proto_item *item;
        proto_tree *tree;
 
-       if (bytes != 2 && bytes != 4) {
-               THROW(ReportedBoundsError);
-       }
-
-       /*
-        * The actual bits of interest appear to only be a USHORT
-        */
-       /* FIXME if this ever changes! */
        mask = tvb_get_letohs(tvb, offset);
 
        if(parent_tree){
-               item = proto_tree_add_text(parent_tree, tvb, offset, bytes,
-                       "File Attributes: 0x%08x", mask);
+               item = proto_tree_add_text(parent_tree, tvb, offset, 2,
+                       "File Attributes: 0x%04x", mask);
                tree = proto_item_add_subtree(item, ett_smb_file_attributes);
 
-               proto_tree_add_boolean(tree, hf_smb_file_attr_encrypted,
-                                      tvb, offset, bytes, mask);
-               proto_tree_add_boolean(tree, hf_smb_file_attr_not_content_indexed,
-                                      tvb, offset, bytes, mask);
-               proto_tree_add_boolean(tree, hf_smb_file_attr_offline,
-                                      tvb, offset, bytes, mask);
-               proto_tree_add_boolean(tree, hf_smb_file_attr_compressed,
-                                      tvb, offset, bytes, mask);
-               proto_tree_add_boolean(tree, hf_smb_file_attr_reparse,
-                                      tvb, offset, bytes, mask);
-               proto_tree_add_boolean(tree, hf_smb_file_attr_sparse,
-                                      tvb, offset, bytes, mask);
-               proto_tree_add_boolean(tree, hf_smb_file_attr_temporary,
-                                      tvb, offset, bytes, mask);
-               proto_tree_add_boolean(tree, hf_smb_file_attr_normal,
-                                      tvb, offset, bytes, mask);
-               proto_tree_add_boolean(tree, hf_smb_file_attr_device,
-                                      tvb, offset, bytes, mask);
                proto_tree_add_boolean(tree, hf_smb_file_attr_archive_16bit,
-                               tvb, offset, bytes, mask);
+                               tvb, offset, 2, mask);
                proto_tree_add_boolean(tree, hf_smb_file_attr_directory_16bit,
-                               tvb, offset, bytes, mask);
+                               tvb, offset, 2, mask);
                proto_tree_add_boolean(tree, hf_smb_file_attr_volume_16bit,
-                               tvb, offset, bytes, mask);
+                               tvb, offset, 2, mask);
                proto_tree_add_boolean(tree, hf_smb_file_attr_system_16bit,
-                               tvb, offset, bytes, mask);
+                               tvb, offset, 2, mask);
                proto_tree_add_boolean(tree, hf_smb_file_attr_hidden_16bit,
-                               tvb, offset, bytes, mask);
+                               tvb, offset, 2, mask);
                proto_tree_add_boolean(tree, hf_smb_file_attr_read_only_16bit,
-                               tvb, offset, bytes, mask);
+                               tvb, offset, 2, mask);
        }
 
-       offset += bytes;
+       offset += 2;
 
        return offset;
 }
 
-/* 3.11 */
+/*
+ * 3.11 in the SNIA CIFS spec
+ * SMB_EXT_FILE_ATTR, section 2.2.1.2.3 in the [MS-CIFS] spec
+ */
 static int
 dissect_file_ext_attr_bits(tvbuff_t *tvb, proto_tree *parent_tree, int offset,
     int len, guint32 mask)
@@ -1705,7 +1690,7 @@ dissect_file_ext_attr_bits(tvbuff_t *tvb, proto_tree *parent_tree, int offset,
 }
 
 /* 3.11 */
-static int
+int
 dissect_file_ext_attr(tvbuff_t *tvb, proto_tree *parent_tree, int offset)
 {
        guint32 mask;
@@ -1775,6 +1760,10 @@ static const true_false_string tfs_search_attribute_archive = {
        "Do NOT include archive files in search results"
 };
 
+/*
+ * Dissects an SMB_FILE_ATTRIBUTES, to use the term given to it by
+ * section 2.2.1.2.4 of [MS-CIFS], in cases where it's search attributes.
+ */
 static int
 dissect_search_attributes(tvbuff_t *tvb, proto_tree *parent_tree, int offset)
 {
@@ -2206,7 +2195,7 @@ dissect_negprot_response(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, in
 
        if (si->sip && si->sip->extra_info_type==SMB_EI_DIALECTS) {
                dialects = si->sip->extra_info;
-               if (dialect <= dialects->num) {
+               if (dialect < dialects->num) {
                        dialect_name = dialects->name[dialect];
                }
        }
@@ -2219,7 +2208,7 @@ dissect_negprot_response(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, in
                if(dialect==0xffff){
                        proto_tree_add_uint_format(tree, hf_smb_dialect_index,
                                tvb, offset, 2, dialect,
-                               "Selected Index: -1, PC NETWORK PROGRAM 1.0 choosen");
+                               "Selected Index: -1, PC NETWORK PROGRAM 1.0 chosen");
                } else {
                        proto_tree_add_uint(tree, hf_smb_dialect_index,
                                tvb, offset, 2, dialect);
@@ -3445,6 +3434,10 @@ dissect_smb_fid(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, int offset,
        proto_item *it;
        proto_tree *tr;
        smb_fid_info_t *fid_info=NULL;
+        smb_fid_info_t *suspect_fid_info=NULL;
+        /* We need this to use an array-accessed tree */
+        GSList          *GSL_iterator;
+        int             found=0;
 
        DISSECTOR_ASSERT(si);
 
@@ -3461,17 +3454,38 @@ dissect_smb_fid(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, int offset,
                fid_info->opened_in=pinfo->fd->num;
                fid_info->closed_in=0;
                fid_info->type=SMB_FID_TYPE_UNKNOWN;
+                fid_info->fid=fid;
+                fid_info->tid=si->tid;
                if(si->sip && (si->sip->extra_info_type==SMB_EI_FILEDATA)){
                        fid_info->fsi=si->sip->extra_info;
                } else {
                        fid_info->fsi=NULL;
                }
-
-               se_tree_insert32(si->ct->fid_tree, fid, fid_info);
+                /* We don't use the fid_tree anymore to access and
+                   maintain the fid information of analized files.
+                   (was se_tree_insert32(si->ct->fid_tree, fid, fid_info);)
+                   We'll use a single list instead to keep track of the
+                   files (fid) opened.
+                   Note that the insert_sorted function allows to insert duplicates
+                   but being inside this if section should prevent it */
+                si->ct->GSL_fid_info=g_slist_insert_sorted(
+                                        si->ct->GSL_fid_info,
+                                        fid_info,
+                                        (GCompareFunc)fid_cmp);
        }
 
        if(!fid_info){
-               fid_info=se_tree_lookup32(si->ct->fid_tree, fid);
+                /* we use the single linked list to access this fid_info
+                   (was fid_info=se_tree_lookup32(si->ct->fid_tree, fid);) */
+                GSL_iterator = si->ct->GSL_fid_info;
+                while (GSL_iterator) {
+                        suspect_fid_info=GSL_iterator->data;
+                        if(suspect_fid_info->opened_in > pinfo->fd->num) break;
+                        if(suspect_fid_info->tid==si->tid && suspect_fid_info->fid==fid)
+                                fid_info=suspect_fid_info;
+                        GSL_iterator=g_slist_next(GSL_iterator);
+                        found+=1;
+                }
        }
        if(!fid_info){
                return NULL;
@@ -3537,7 +3551,7 @@ dissect_open_file_response(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *tr
        offset += 2;
 
        /* File Attributes */
-       offset = dissect_file_attributes(tvb, tree, offset, 2);
+       offset = dissect_file_attributes(tvb, tree, offset);
 
        /* last write time */
        offset = dissect_smb_UTIME(tvb, tree, offset, hf_smb_last_write_time);
@@ -3696,7 +3710,7 @@ dissect_create_file_request(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
        WORD_COUNT;
 
        /* file attributes */
-       offset = dissect_file_attributes(tvb, tree, offset, 2);
+       offset = dissect_file_attributes(tvb, tree, offset);
 
        /* creation time */
        offset = dissect_smb_UTIME(tvb, tree, offset, hf_smb_create_time);
@@ -3988,7 +4002,7 @@ dissect_query_information_response(tvbuff_t *tvb, packet_info *pinfo _U_, proto_
        WORD_COUNT;
 
        /* File Attributes */
-       offset = dissect_file_attributes(tvb, tree, offset, 2);
+       offset = dissect_file_attributes(tvb, tree, offset);
 
        /* Last Write Time */
        offset = dissect_smb_UTIME(tvb, tree, offset, hf_smb_last_write_time);
@@ -4022,7 +4036,7 @@ dissect_set_information_request(tvbuff_t *tvb, packet_info *pinfo, proto_tree *t
        WORD_COUNT;
 
        /* file attributes */
-       offset = dissect_file_attributes(tvb, tree, offset, 2);
+       offset = dissect_file_attributes(tvb, tree, offset);
 
        /* last write time */
        offset = dissect_smb_UTIME(tvb, tree, offset, hf_smb_last_write_time);
@@ -4209,7 +4223,7 @@ dissect_read_file_response(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *tr
        /* file data, might be DCERPC on a pipe */
        if(bc){
                offset = dissect_file_data_maybe_dcerpc(tvb, pinfo, tree,
-                   top_tree, offset, bc, bc, 0, (guint16) fid);
+                   top_tree_global, offset, bc, bc, 0, (guint16) fid);
                bc = 0;
        }
 
@@ -4253,7 +4267,7 @@ dissect_lock_and_read_response(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree
 }
 
 typedef struct _rw_info_t {
-       guint32 offset;
+       guint64 offset;
        guint32 len;
        guint16 fid;
 } rw_info_t;
@@ -4308,7 +4322,7 @@ dissect_write_file_request(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *tr
        if(rwi){
                proto_item *it;
 
-               it=proto_tree_add_uint(tree, hf_smb_file_rw_offset, tvb, 0, 0, rwi->offset);
+               it=proto_tree_add_uint64(tree, hf_smb_file_rw_offset, tvb, 0, 0, rwi->offset);
 
                PROTO_ITEM_SET_GENERATED(it);
                it=proto_tree_add_uint(tree, hf_smb_file_rw_length, tvb, 0, 0, rwi->len);
@@ -4334,7 +4348,7 @@ dissect_write_file_request(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *tr
        /* file data, might be DCERPC on a pipe */
        if (bc != 0) {
                offset = dissect_file_data_maybe_dcerpc(tvb, pinfo, tree,
-                   top_tree, offset, bc, bc, ofs, fid);
+                   top_tree_global, offset, bc, bc, ofs, fid);
                bc = 0;
        }
 
@@ -4370,7 +4384,7 @@ dissect_write_file_response(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *t
        if(rwi){
                proto_item *it;
 
-               it=proto_tree_add_uint(tree, hf_smb_file_rw_offset, tvb, 0, 0, rwi->offset);
+               it=proto_tree_add_uint64(tree, hf_smb_file_rw_offset, tvb, 0, 0, rwi->offset);
 
                PROTO_ITEM_SET_GENERATED(it);
                it=proto_tree_add_uint(tree, hf_smb_file_rw_length, tvb, 0, 0, rwi->len);
@@ -4618,7 +4632,7 @@ dissect_query_information2_response(tvbuff_t *tvb, packet_info *pinfo _U_, proto
        offset += 4;
 
        /* File Attributes */
-       offset = dissect_file_attributes(tvb, tree, offset, 2);
+       offset = dissect_file_attributes(tvb, tree, offset);
 
        BYTE_COUNT;
 
@@ -4697,26 +4711,26 @@ dissect_write_and_close_response(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tr
    available at http://us1.samba.org/samba/ftp/SMB-info/DOSEXTP.TXT
 */
 static gchar *
-smbext20_timeout_msecs_to_str(gint32 time)
+smbext20_timeout_msecs_to_str(gint32 timeout)
 {
         gchar *buf;
 #define SMBEXT20_TIMEOUT_MSECS_TO_STR_MAXLEN 60
 
-       if (time <= 0) {
+       if (timeout <= 0) {
                buf=ep_alloc(SMBEXT20_TIMEOUT_MSECS_TO_STR_MAXLEN+1);
-               if (time == 0) {
+               if (timeout == 0) {
                        g_snprintf(buf, SMBEXT20_TIMEOUT_MSECS_TO_STR_MAXLEN+1, "Return immediately (0)");
-               } else if (time == -1) {
+               } else if (timeout == -1) {
                        g_snprintf(buf, SMBEXT20_TIMEOUT_MSECS_TO_STR_MAXLEN+1, "Wait indefinitely (-1)");
-               } else if (time == -2) {
+               } else if (timeout == -2) {
                        g_snprintf(buf, SMBEXT20_TIMEOUT_MSECS_TO_STR_MAXLEN+1, "Use default timeout (-2)");
                } else {
-                       g_snprintf(buf, SMBEXT20_TIMEOUT_MSECS_TO_STR_MAXLEN+1, "Unknown reserved value (%d)", time);
+                       g_snprintf(buf, SMBEXT20_TIMEOUT_MSECS_TO_STR_MAXLEN+1, "Unknown reserved value (%d)", timeout);
                }
                return buf;
        }
 
-       return time_msecs_to_str(time);
+       return time_msecs_to_str(timeout);
 }
 
 static int
@@ -5570,8 +5584,8 @@ dissect_locking_andx_request(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *
                        "Unlocks");
                tr = proto_item_add_subtree(it, ett_smb_unlocks);
                while(un--){
-                       proto_item *litem = NULL;
-                       proto_tree *ltree = NULL;
+                       proto_item *litem_2 = NULL;
+                       proto_tree *ltree_2 = NULL;
                        if(lt&0x10){
                                guint64 val;
                                guint16 lock_pid;
@@ -5579,19 +5593,19 @@ dissect_locking_andx_request(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *
                                guint64 lock_length;
 
                                /* large lock format */
-                               litem = proto_tree_add_text(tr, tvb, offset, 20,
+                               litem_2 = proto_tree_add_text(tr, tvb, offset, 20,
                                        "Unlock");
-                               ltree = proto_item_add_subtree(litem, ett_smb_unlock);
+                               ltree_2 = proto_item_add_subtree(litem_2, ett_smb_unlock);
 
                                /* PID */
                                CHECK_BYTE_COUNT(2);
                                lock_pid=tvb_get_letohs(tvb, offset);
-                               proto_tree_add_item(ltree, hf_smb_pid, tvb, offset, 2, TRUE);
+                               proto_tree_add_item(ltree_2, hf_smb_pid, tvb, offset, 2, TRUE);
                                COUNT_BYTES(2);
 
                                /* 2 reserved bytes */
                                CHECK_BYTE_COUNT(2);
-                               proto_tree_add_item(ltree, hf_smb_reserved, tvb, offset, 2, TRUE);
+                               proto_tree_add_item(ltree_2, hf_smb_reserved, tvb, offset, 2, TRUE);
                                COUNT_BYTES(2);
 
                                /* offset */
@@ -5599,7 +5613,7 @@ dissect_locking_andx_request(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *
                                val=((guint64)tvb_get_letohl(tvb, offset)) << 32
                                    | tvb_get_letohl(tvb, offset+4);
                                lock_offset=val;
-                               proto_tree_add_uint64(ltree, hf_smb_lock_long_offset, tvb, offset, 8, val);
+                               proto_tree_add_uint64(ltree_2, hf_smb_lock_long_offset, tvb, offset, 8, val);
                                COUNT_BYTES(8);
 
                                /* length */
@@ -5607,7 +5621,7 @@ dissect_locking_andx_request(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *
                                val=((guint64)tvb_get_letohl(tvb, offset)) << 32
                                    | tvb_get_letohl(tvb, offset+4);
                                lock_length=val;
-                               proto_tree_add_uint64(ltree, hf_smb_lock_long_length, tvb, offset, 8, val);
+                               proto_tree_add_uint64(ltree_2, hf_smb_lock_long_length, tvb, offset, 8, val);
                                COUNT_BYTES(8);
 
                                /* remember the unlock for the reply */
@@ -5622,23 +5636,23 @@ dissect_locking_andx_request(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *
                                }
                        } else {
                                /* normal lock format */
-                               litem = proto_tree_add_text(tr, tvb, offset, 10,
+                               litem_2 = proto_tree_add_text(tr, tvb, offset, 10,
                                        "Unlock");
-                               ltree = proto_item_add_subtree(litem, ett_smb_unlock);
+                               ltree_2 = proto_item_add_subtree(litem_2, ett_smb_unlock);
 
                                /* PID */
                                CHECK_BYTE_COUNT(2);
-                               proto_tree_add_item(ltree, hf_smb_pid, tvb, offset, 2, TRUE);
+                               proto_tree_add_item(ltree_2, hf_smb_pid, tvb, offset, 2, TRUE);
                                COUNT_BYTES(2);
 
                                /* offset */
                                CHECK_BYTE_COUNT(4);
-                               proto_tree_add_item(ltree, hf_smb_offset, tvb, offset, 4, TRUE);
+                               proto_tree_add_item(ltree_2, hf_smb_offset, tvb, offset, 4, TRUE);
                                COUNT_BYTES(4);
 
                                /* lock count */
                                CHECK_BYTE_COUNT(4);
-                               proto_tree_add_item(ltree, hf_smb_count, tvb, offset, 4, TRUE);
+                               proto_tree_add_item(ltree_2, hf_smb_count, tvb, offset, 4, TRUE);
                                COUNT_BYTES(4);
                        }
                }
@@ -5654,8 +5668,8 @@ dissect_locking_andx_request(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *
                        "Locks");
                tr = proto_item_add_subtree(it, ett_smb_locks);
                while(ln--){
-                       proto_item *litem = NULL;
-                       proto_tree *ltree = NULL;
+                       proto_item *litem_2 = NULL;
+                       proto_tree *ltree_2 = NULL;
                        if(lt&0x10){
                                guint64 val;
                                guint16 lock_pid;
@@ -5663,19 +5677,19 @@ dissect_locking_andx_request(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *
                                guint64 lock_length;
 
                                /* large lock format */
-                               litem = proto_tree_add_text(tr, tvb, offset, 20,
+                               litem_2 = proto_tree_add_text(tr, tvb, offset, 20,
                                        "Lock");
-                               ltree = proto_item_add_subtree(litem, ett_smb_lock);
+                               ltree_2 = proto_item_add_subtree(litem_2, ett_smb_lock);
 
                                /* PID */
                                CHECK_BYTE_COUNT(2);
                                lock_pid=tvb_get_letohs(tvb, offset);
-                               proto_tree_add_item(ltree, hf_smb_pid, tvb, offset, 2, TRUE);
+                               proto_tree_add_item(ltree_2, hf_smb_pid, tvb, offset, 2, TRUE);
                                COUNT_BYTES(2);
 
                                /* 2 reserved bytes */
                                CHECK_BYTE_COUNT(2);
-                               proto_tree_add_item(ltree, hf_smb_reserved, tvb, offset, 2, TRUE);
+                               proto_tree_add_item(ltree_2, hf_smb_reserved, tvb, offset, 2, TRUE);
                                COUNT_BYTES(2);
 
                                /* offset */
@@ -5683,7 +5697,7 @@ dissect_locking_andx_request(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *
                                val=((guint64)tvb_get_letohl(tvb, offset)) << 32
                                    | tvb_get_letohl(tvb, offset+4);
                                lock_offset=val;
-                               proto_tree_add_uint64(ltree, hf_smb_lock_long_offset, tvb, offset, 8, val);
+                               proto_tree_add_uint64(ltree_2, hf_smb_lock_long_offset, tvb, offset, 8, val);
                                COUNT_BYTES(8);
 
                                /* length */
@@ -5691,7 +5705,7 @@ dissect_locking_andx_request(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *
                                val=((guint64)tvb_get_letohl(tvb, offset)) << 32
                                    | tvb_get_letohl(tvb, offset+4);
                                lock_length=val;
-                               proto_tree_add_uint64(ltree, hf_smb_lock_long_length, tvb, offset, 8, val);
+                               proto_tree_add_uint64(ltree_2, hf_smb_lock_long_length, tvb, offset, 8, val);
                                COUNT_BYTES(8);
 
                                /* remember the lock for the reply */
@@ -5706,23 +5720,23 @@ dissect_locking_andx_request(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *
                                }
                        } else {
                                /* normal lock format */
-                               litem = proto_tree_add_text(tr, tvb, offset, 10,
+                               litem_2 = proto_tree_add_text(tr, tvb, offset, 10,
                                        "Lock");
-                               ltree = proto_item_add_subtree(litem, ett_smb_lock);
+                               ltree_2 = proto_item_add_subtree(litem_2, ett_smb_lock);
 
                                /* PID */
                                CHECK_BYTE_COUNT(2);
-                               proto_tree_add_item(ltree, hf_smb_pid, tvb, offset, 2, TRUE);
+                               proto_tree_add_item(ltree_2, hf_smb_pid, tvb, offset, 2, TRUE);
                                COUNT_BYTES(2);
 
                                /* offset */
                                CHECK_BYTE_COUNT(4);
-                               proto_tree_add_item(ltree, hf_smb_offset, tvb, offset, 4, TRUE);
+                               proto_tree_add_item(ltree_2, hf_smb_offset, tvb, offset, 4, TRUE);
                                COUNT_BYTES(4);
 
                                /* lock count */
                                CHECK_BYTE_COUNT(4);
-                               proto_tree_add_item(ltree, hf_smb_count, tvb, offset, 4, TRUE);
+                               proto_tree_add_item(ltree_2, hf_smb_count, tvb, offset, 4, TRUE);
                                COUNT_BYTES(4);
                        }
                }
@@ -5983,7 +5997,7 @@ dissect_open_andx_request(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, i
        offset = dissect_search_attributes(tvb, tree, offset);
 
        /* File Attributes */
-       offset = dissect_file_attributes(tvb, tree, offset, 2);
+       offset = dissect_file_attributes(tvb, tree, offset);
 
        /* creation time */
        offset = dissect_smb_UTIME(tvb, tree, offset, hf_smb_create_time);
@@ -6015,6 +6029,18 @@ dissect_open_andx_request(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, i
                fn);
        COUNT_BYTES(fn_len);
 
+        /* Copied this portion of code from create_andx_request
+           to guarantee that fsi and si->sip are always correctly filled out */
+        if((!pinfo->fd->flags.visited) && si->sip && fn){
+                smb_fid_saved_info_t *fsi;
+
+                fsi=se_alloc(sizeof(smb_fid_saved_info_t));
+                fsi->filename=se_strdup(fn);
+
+                si->sip->extra_info_type=SMB_EI_FILEDATA;
+                si->sip->extra_info=fsi;
+        }
+
        if (check_col(pinfo->cinfo, COL_INFO)) {
                col_append_fstr(pinfo->cinfo, COL_INFO, ", Path: %s",
                    format_text(fn, strlen(fn)));
@@ -6053,7 +6079,7 @@ static const value_string ipc_state_read_mode_vals[] = {
 
 int
 dissect_ipc_state(tvbuff_t *tvb, proto_tree *parent_tree, int offset,
-    gboolean setstate)
+    gboolean setstate_flag)
 {
        guint16 mask;
        proto_item *item;
@@ -6068,7 +6094,7 @@ dissect_ipc_state(tvbuff_t *tvb, proto_tree *parent_tree, int offset,
 
                proto_tree_add_boolean(tree, hf_smb_ipc_state_nonblocking,
                        tvb, offset, 2, mask);
-               if (!setstate) {
+               if (!setstate_flag) {
                        proto_tree_add_uint(tree, hf_smb_ipc_state_endpoint,
                                tvb, offset, 2, mask);
                        proto_tree_add_uint(tree, hf_smb_ipc_state_pipe_type,
@@ -6076,7 +6102,7 @@ dissect_ipc_state(tvbuff_t *tvb, proto_tree *parent_tree, int offset,
                }
                proto_tree_add_uint(tree, hf_smb_ipc_state_read_mode,
                        tvb, offset, 2, mask);
-               if (!setstate) {
+               if (!setstate_flag) {
                        proto_tree_add_uint(tree, hf_smb_ipc_state_icount,
                                tvb, offset, 2, mask);
                }
@@ -6093,6 +6119,10 @@ dissect_open_andx_response(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
        guint8  wc, cmd=0xff;
        guint16 andxoffset=0, bc;
        guint16 fid;
+        guint16 ftype;
+        guint16 fattr;
+        smb_fid_info_t *fid_info=NULL;
+        gboolean        isdir=FALSE;
 
        WORD_COUNT;
 
@@ -6116,16 +6146,22 @@ dissect_open_andx_response(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
 
        /* fid */
        fid = tvb_get_letohs(tvb, offset);
-       dissect_smb_fid(tvb, pinfo, tree, offset, 2, fid, TRUE, FALSE, FALSE);
+        /* we add fid_info= to this call so that we save the result */
+        fid_info=dissect_smb_fid(tvb, pinfo, tree, offset, 2, fid, TRUE, FALSE, FALSE);
+
        offset += 2;
 
        /* File Attributes */
-       offset = dissect_file_attributes(tvb, tree, offset, 2);
+        fattr = tvb_get_letohs(tvb, offset);
+        isdir = fattr & SMB_FILE_ATTRIBUTE_DIRECTORY;
+       offset = dissect_file_attributes(tvb, tree, offset);
 
        /* last write time */
        offset = dissect_smb_UTIME(tvb, tree, offset, hf_smb_last_write_time);
 
        /* File Size */
+        /* We store the file_size in the fid_info */
+        fid_info->end_of_file=(guint64) tvb_get_letohl(tvb, offset);
        proto_tree_add_item(tree, hf_smb_file_size, tvb, offset, 4, TRUE);
        offset += 4;
 
@@ -6133,8 +6169,30 @@ dissect_open_andx_response(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
        offset = dissect_access(tvb, tree, offset, "Granted");
 
        /* File Type */
+        ftype=tvb_get_letohs(tvb, offset);
        proto_tree_add_item(tree, hf_smb_file_type, tvb, offset, 2, TRUE);
        offset += 2;
+        /* Copied from dissect_nt_create_andx_response
+           Try to remember the type of this fid so that we can dissect
+           any future security descriptor (access mask) properly
+         */
+        fid_info->type=SMB_FID_TYPE_UNKNOWN;
+        if(ftype==0){
+                if(isdir==0){
+                        if(fid_info){
+                                fid_info->type=SMB_FID_TYPE_FILE;
+                        }
+                } else {
+                        if(fid_info){
+                                fid_info->type=SMB_FID_TYPE_DIR;
+                        }
+                }
+        }
+        if(ftype==2 || ftype==1){
+                if(fid_info){
+                        fid_info->type=SMB_FID_TYPE_PIPE;
+                }
+        }
 
        /* IPC State */
        offset = dissect_ipc_state(tvb, tree, offset, FALSE);
@@ -6170,7 +6228,8 @@ dissect_read_andx_request(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, i
        guint16 andxoffset=0, bc, maxcnt_low;
        guint32 maxcnt_high;
        guint32 maxcnt=0;
-       guint32 ofs = 0;
+       guint32 offsetlow, offsethigh=0;
+       guint64 ofs;
        smb_info_t *si= (smb_info_t *)pinfo->private_data;
        unsigned int fid;
        rw_info_t *rwi=NULL;
@@ -6204,7 +6263,7 @@ dissect_read_andx_request(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, i
        offset += 2;
 
        /* offset */
-       ofs = tvb_get_letohl(tvb, offset);
+       offsetlow = tvb_get_letohl(tvb, offset);
        proto_tree_add_item(tree, hf_smb_offset, tvb, offset, 4, TRUE);
        offset += 4;
 
@@ -6233,10 +6292,24 @@ dissect_read_andx_request(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, i
         * bits in max count, but it does show a 32-bit timeout
         * after the min count field.
         *
-        * Perhaps the 32-bit timeout field was hijacked as a 16-bit
-        * high count and a 16-bit reserved field.
+        * The Microsoft [MS-SMB] spec shows it as a ULONG named
+        * Timeout_or_MaxCountHigh, which is
+        *
+        *      ...extended to be treated as a union of a 32-bit
+        *      Timeout field and a 16-bit MaxCountHigh field.
+        *      When reading from a regular file, the field
+        *      MUST be interpreted as MaxCountHigh and the
+        *      two unused bytes MUST be zero.  When reading from
+        *      a name[sic] pipe or I/O device, the field MUST
+        *      be interpreted as Timeout.
         *
-        * We fetch and display it as 32 bits.
+        * Timeout is a timeout in milliseconds, with 0xffffffff
+        * and 0xfffffffe having special meaning.
+        *
+        * MaxCountHigh is 16 bits of the MaxCountHigh value
+        * followed by 16 bits of Reserved.
+        *
+        * We fetch and display it as 32 bits for now.
          *
          * XXX if maxcount high is 0xFFFFFFFF we assume it is just padding
         * bytes and we just ignore it.
@@ -6253,10 +6326,24 @@ dissect_read_andx_request(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, i
        maxcnt=maxcnt_high;
        maxcnt=(maxcnt<<16)|maxcnt_low;
 
+       /* remaining */
+       proto_tree_add_item(tree, hf_smb_remaining, tvb, offset, 2, TRUE);
+       offset += 2;
+
+       if(wc==12){
+               /* high offset */
+               offsethigh=tvb_get_letohl(tvb, offset);
+               proto_tree_add_item(tree, hf_smb_high_offset, tvb, offset, 4, TRUE);
+               offset += 4;
+       }
+
+       ofs=offsethigh;
+       ofs=(ofs<<32)|offsetlow;
+
        if (check_col(pinfo->cinfo, COL_INFO))
                col_append_fstr(pinfo->cinfo, COL_INFO,
-                               ", %u byte%s at offset %u", maxcnt,
-                               (maxcnt == 1) ? "" : "s", ofs);
+                               ", %u byte%s at offset %" G_GINT64_MODIFIER "u",
+                               maxcnt, (maxcnt == 1) ? "" : "s", ofs);
 
        /* save the offset/len for this transaction */
        if(si->sip && !pinfo->fd->flags.visited){
@@ -6274,23 +6361,13 @@ dissect_read_andx_request(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, i
        if(rwi){
                proto_item *it;
 
-               it=proto_tree_add_uint(tree, hf_smb_file_rw_offset, tvb, 0, 0, rwi->offset);
+               it=proto_tree_add_uint64(tree, hf_smb_file_rw_offset, tvb, 0, 0, rwi->offset);
 
                PROTO_ITEM_SET_GENERATED(it);
                it=proto_tree_add_uint(tree, hf_smb_file_rw_length, tvb, 0, 0, rwi->len);
                PROTO_ITEM_SET_GENERATED(it);
        }
 
-       /* remaining */
-       proto_tree_add_item(tree, hf_smb_remaining, tvb, offset, 2, TRUE);
-       offset += 2;
-
-       if(wc==12){
-               /* high offset */
-               proto_tree_add_item(tree, hf_smb_high_offset, tvb, offset, 4, TRUE);
-               offset += 4;
-       }
-
        BYTE_COUNT;
 
        END_OF_SMB
@@ -6304,6 +6381,15 @@ dissect_read_andx_request(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, i
        return offset;
 }
 
+/* Strings that describes the SMB object type */
+const value_string smb_fid_types[] = {
+        {SMB_FID_TYPE_UNKNOWN,"UNKNOWN"},
+        {SMB_FID_TYPE_FILE,"FILE"},
+        {SMB_FID_TYPE_DIR,"DIRECTORY (Not Implemented)"},
+        {SMB_FID_TYPE_PIPE,"PIPE (Not Implemented)"},
+       {0, NULL}
+};
+
 static int
 dissect_read_andx_response(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, int offset, proto_tree *smb_tree)
 {
@@ -6311,8 +6397,18 @@ dissect_read_andx_response(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
        guint16 andxoffset=0, bc, datalen_low, dataoffset=0;
        guint32 datalen=0, datalen_high;
        smb_info_t *si = (smb_info_t *)pinfo->private_data;
-       int fid=0;
        rw_info_t *rwi=NULL;
+        guint16 fid=0; /* was int fid=0; */
+
+        smb_eo_t        *eo_info; /* eo_info variable to pass info. to
+                                     export object and aux */
+        smb_tid_info_t  *tid_info=NULL;
+        smb_fid_info_t  *fid_info=NULL;
+        smb_fid_info_t  *suspect_fid_info=NULL;
+        guint32 tvblen,packet_number;
+        tvbuff_t        *data_tvb;
+        GSList          *GSL_iterator;
+        int             found=0;
 
        DISSECTOR_ASSERT(si);
 
@@ -6349,7 +6445,7 @@ dissect_read_andx_response(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
        if(rwi){
                proto_item *it;
 
-               it=proto_tree_add_uint(tree, hf_smb_file_rw_offset, tvb, 0, 0, rwi->offset);
+               it=proto_tree_add_uint64(tree, hf_smb_file_rw_offset, tvb, 0, 0, rwi->offset);
 
                PROTO_ITEM_SET_GENERATED(it);
                it=proto_tree_add_uint(tree, hf_smb_file_rw_length, tvb, 0, 0, rwi->len);
@@ -6381,7 +6477,14 @@ dissect_read_andx_response(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
        proto_tree_add_uint(tree, hf_smb_data_offset, tvb, offset, 2, dataoffset);
        offset += 2;
 
-       /* XXX we should really only do this in case we have seen LARGE FILE being negotiated */
+       /*
+        * XXX - the SNIA SMB spec says this is a USHORT, not a
+        * ULONG.
+        *
+        * XXX - we should really only do this in case we have seen
+        * LARGE FILE being negotiated.  Unfortunately, we might not
+        * have seen the negotiation phase in the capture....
+        */
        /* data length high */
        datalen_high = tvb_get_letohl(tvb, offset);
        if(datalen_high==0xffffffff){
@@ -6410,10 +6513,55 @@ dissect_read_andx_response(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
        /* file data, might be DCERPC on a pipe */
        if(bc){
                offset = dissect_file_data_maybe_dcerpc(tvb, pinfo, tree,
-                   top_tree, offset, bc, (guint16) datalen, 0, (guint16) fid);
+                   top_tree_global, offset, bc, (guint16) datalen, 0, (guint16) fid);
                bc = 0;
        }
 
+        /* feed the export object tap listener */
+        tvblen = tvb_length_remaining(tvb, dataoffset);
+        if(have_tap_listener(smb_eo_tap) && datalen==tvblen && rwi) {
+                packet_number=pinfo->fd->num;
+                /* Create a new tvb to point to the payload data */
+                data_tvb = tvb_new_subset(tvb, dataoffset, datalen, tvblen);
+                /* Create the eo_info to pass to the listener */
+                eo_info = ep_alloc(sizeof(smb_eo_t));
+
+                /* Try to get fid_info and tid_info */
+                if (fid_info==NULL) {
+                        GSL_iterator = si->ct->GSL_fid_info;
+                        while (GSL_iterator) {
+                                suspect_fid_info=GSL_iterator->data;
+                                if(suspect_fid_info->opened_in > pinfo->fd->num) break;
+                                if(suspect_fid_info->tid==si->tid && suspect_fid_info->fid==fid)
+                                        fid_info=suspect_fid_info;
+                                GSL_iterator=g_slist_next(GSL_iterator);
+                                found+=1;
+                        }
+                }
+                tid_info = se_tree_lookup32(si->ct->tid_tree, si->tid);
+
+                /* Construct the eo_info structure */
+                if (tid_info)   eo_info->hostname = tid_info->filename;
+                else            eo_info->hostname = ep_strdup_printf("\\\\TREEID_%i",si->tid);
+                if (fid_info) {
+                        eo_info->filename=NULL;
+                        if (fid_info->fsi)
+                                if (fid_info->fsi->filename)
+                                        eo_info->filename = (gchar *) fid_info->fsi->filename;
+                        if(!eo_info->filename) eo_info->filename = ep_strdup_printf("\\FILEID_%i",fid);
+                        eo_info->fid_type = fid_info->type;                                             eo_info->end_of_file = fid_info->end_of_file;
+                } else {                                                                                eo_info->fid_type=SMB_FID_TYPE_UNKNOWN;
+                        eo_info->filename = ep_strdup_printf("\\FILEID_%i",fid);                        eo_info->end_of_file = 0;
+                }                                                                               eo_info->fid=fid;
+                eo_info->tid=si->tid;                                                           eo_info->uid=si->uid;
+                eo_info->payload_len = datalen;                                                 eo_info->payload_data = data_tvb->real_data;
+                eo_info->smb_file_offset=rwi->offset;                                           eo_info->smb_chunk_len=rwi->len;
+                eo_info->cmd=SMB_COM_READ_ANDX;
+                /* Queue data to the listener */
+
+                tap_queue_packet(smb_eo_tap, pinfo, eo_info);
+        }
+
        END_OF_SMB
 
        if (cmd != 0xff) {      /* there is an andX command */
@@ -6428,15 +6576,25 @@ dissect_read_andx_response(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
 static int
 dissect_write_andx_request(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, int offset, proto_tree *smb_tree)
 {
-       guint32 ofs=0;
        guint8  wc, cmd=0xff;
        guint16 andxoffset=0, bc, dataoffset=0, datalen_low, datalen_high;
+       guint32 offsetlow, offsethigh=0;
+       guint64 ofs;
        guint32 datalen=0;
        smb_info_t *si = (smb_info_t *)pinfo->private_data;
-       unsigned int fid=0;
+        guint16 fid=0; /* was unsigned int fid=0; */
        guint16 mode = 0;
        rw_info_t *rwi=NULL;
-
+        /* eo_info variables to pass info. to export object and
+           other aux */
+        smb_eo_t        *eo_info;
+        smb_tid_info_t  *tid_info=NULL;
+        smb_fid_info_t  *fid_info=NULL;
+        smb_fid_info_t  *suspect_fid_info=NULL;
+        guint32 tvblen,packet_number;
+        tvbuff_t        *data_tvb;
+        GSList          *GSL_iterator;
+        int             found=0;
 
        DISSECTOR_ASSERT(si);
 
@@ -6466,7 +6624,7 @@ dissect_write_andx_request(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
        offset += 2;
 
        /* offset */
-       ofs = tvb_get_letohl(tvb, offset);
+       offsetlow = tvb_get_letohl(tvb, offset);
        proto_tree_add_item(tree, hf_smb_offset, tvb, offset, 4, TRUE);
        offset += 4;
 
@@ -6482,7 +6640,11 @@ dissect_write_andx_request(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
        proto_tree_add_item(tree, hf_smb_remaining, tvb, offset, 2, TRUE);
        offset += 2;
 
-       /* XXX we should really only do this in case we have seen LARGE FILE being negotiated */
+       /*
+        * XXX - we should really only do this in case we have seen
+        * LARGE FILE being negotiated.  Unfortunately, we might not
+        * have seen the negotiation phase in the capture....
+        */
        /* data length high */
        datalen_high = tvb_get_letohs(tvb, offset);
        proto_tree_add_uint(tree, hf_smb_data_len_high, tvb, offset, 2, datalen_high);
@@ -6501,11 +6663,20 @@ dissect_write_andx_request(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
        proto_tree_add_uint(tree, hf_smb_data_offset, tvb, offset, 2, dataoffset);
        offset += 2;
 
-       /* FIXME: handle Large (48-bit) byte/offset to COL_INFO */
+       if(wc==14){
+               /* high offset */
+               offsethigh=tvb_get_letohl(tvb, offset);
+               proto_tree_add_item(tree, hf_smb_high_offset, tvb, offset, 4, TRUE);
+               offset += 4;
+       }
+
+       ofs=offsethigh;
+       ofs=(ofs<<32)|offsetlow;
+
        if (check_col(pinfo->cinfo, COL_INFO))
                col_append_fstr(pinfo->cinfo, COL_INFO,
-                               ", %u byte%s at offset %u", datalen,
-                               (datalen == 1) ? "" : "s", ofs);
+                               ", %u byte%s at offset %" G_GINT64_MODIFIER "u",
+                               datalen, (datalen == 1) ? "" : "s", ofs);
 
        /* save the offset/len for this transaction */
        if(si->sip && !pinfo->fd->flags.visited){
@@ -6523,7 +6694,7 @@ dissect_write_andx_request(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
        if(rwi){
                proto_item *it;
 
-               it=proto_tree_add_uint(tree, hf_smb_file_rw_offset, tvb, 0, 0, rwi->offset);
+               it=proto_tree_add_uint64(tree, hf_smb_file_rw_offset, tvb, 0, 0, rwi->offset);
 
                PROTO_ITEM_SET_GENERATED(it);
                it=proto_tree_add_uint(tree, hf_smb_file_rw_length, tvb, 0, 0, rwi->len);
@@ -6531,12 +6702,6 @@ dissect_write_andx_request(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
        }
 
 
-       if(wc==14){
-               /* high offset */
-               proto_tree_add_item(tree, hf_smb_high_offset, tvb, offset, 4, TRUE);
-               offset += 4;
-       }
-
        BYTE_COUNT;
 
        /* if both the MessageStart and the  WriteRawNamedPipe flags are set
@@ -6572,10 +6737,69 @@ dissect_write_andx_request(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
        /* file data, might be DCERPC on a pipe */
        if (bc != 0) {
                offset = dissect_file_data_maybe_dcerpc(tvb, pinfo, tree,
-                   top_tree, offset, bc, (guint16) datalen, 0, (guint16) fid);
+                   top_tree_global, offset, bc, (guint16) datalen, 0, (guint16) fid);
                bc = 0;
        }
 
+        /* feed the export object tap listener */
+        tvblen = tvb_length_remaining(tvb, dataoffset);
+        if(have_tap_listener(smb_eo_tap) && datalen==tvblen && rwi) {
+                packet_number=pinfo->fd->num;
+                /* Create a new tvb to point to the payload data */
+                data_tvb = tvb_new_subset(tvb, dataoffset, datalen, tvblen);
+                /* Create the eo_info to pass to the listener */
+                eo_info = ep_alloc(sizeof(smb_eo_t));
+
+                /* Try to get fid_info and tid_info */
+                if (fid_info==NULL) {
+                        /* We'll use a GSL instead */
+                        /* (was fid_info = se_tree_lookup32(si->ct->fid_tree, fi
+d);) */
+                        GSL_iterator = si->ct->GSL_fid_info;
+                        while (GSL_iterator) {
+                                suspect_fid_info=GSL_iterator->data;
+                                if(suspect_fid_info->opened_in > pinfo->fd->num)
+ break;
+                                if(suspect_fid_info->tid==si->tid && suspect_fid_info->fid==fid)
+                                        fid_info=suspect_fid_info;
+                                GSL_iterator=g_slist_next(GSL_iterator);
+                                found+=1;
+                        }
+                }
+                tid_info = se_tree_lookup32(si->ct->tid_tree, si->tid);
+
+                /* Construct the eo_info structure */
+                if (tid_info)   eo_info->hostname = tid_info->filename;
+                else            eo_info->hostname = ep_strdup_printf("\\\\TREEID_%i",si->tid);
+                if (fid_info) {
+                        eo_info->filename=NULL;
+                        if (fid_info->fsi) {
+                                if (fid_info->fsi->filename) {
+                                        eo_info->filename = (gchar *) fid_info->fsi->filename;
+                                        }
+                                }
+                        if(!eo_info->filename) eo_info->filename = ep_strdup_printf("\\FILEID_%i",fid);
+                        eo_info->fid_type = fid_info->type;
+                        eo_info->end_of_file = fid_info->end_of_file;
+                } else {
+                        eo_info->fid_type=SMB_FID_TYPE_UNKNOWN;
+                        eo_info->filename = ep_strdup_printf("\\FILEID_%i",fid);
+                        eo_info->end_of_file = 0;
+                }
+                eo_info->fid=fid;
+                eo_info->tid=si->tid;
+                eo_info->uid=si->uid;
+                eo_info->payload_len = datalen;
+                eo_info->payload_data = data_tvb->real_data;
+                eo_info->smb_file_offset=rwi->offset;
+                eo_info->smb_chunk_len=rwi->len;
+                eo_info->cmd=SMB_COM_WRITE_ANDX;
+
+                /* Queue data to the listener */
+
+                tap_queue_packet(smb_eo_tap, pinfo, eo_info);
+        }
+
        END_OF_SMB
 
        if (cmd != 0xff) {      /* there is an andX command */
@@ -6625,7 +6849,7 @@ dissect_write_andx_response(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
        if(rwi){
                proto_item *it;
 
-               it=proto_tree_add_uint(tree, hf_smb_file_rw_offset, tvb, 0, 0, rwi->offset);
+               it=proto_tree_add_uint64(tree, hf_smb_file_rw_offset, tvb, 0, 0, rwi->offset);
 
                PROTO_ITEM_SET_GENERATED(it);
                it=proto_tree_add_uint(tree, hf_smb_file_rw_length, tvb, 0, 0, rwi->len);
@@ -7255,6 +7479,11 @@ dissect_empty_andx(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, int offs
        return offset;
 }
 
+       /*
+        * From [MS-SMB] - v20100711 Server Message Block (SMB) Protocol Specification
+        * http://download.microsoft.com/download/a/e/6/ae6e4142-aa58-45c6-8dcf-a657e5900cd3/%5BMS-SMB%5D.pdf
+        * 2.2.4.7 SMB_COM_TREE_CONNECT_ANDX (0x75)
+        */
 
 static const true_false_string tfs_connect_support_search = {
        "Exclusive search bits supported",
@@ -7264,6 +7493,21 @@ static const true_false_string tfs_connect_support_in_dfs = {
        "Share is in Dfs",
        "Share isn't in Dfs"
 };
+static const value_string connect_support_csc_mask_vals[] = {
+       { 0,    "Automatic file-to-file reintegration NOT permitted"},
+       { 1,    "Automatic file-to-file reintegration permitted"},
+       { 2,    "Offline caching allow for the share"},
+       { 3,    "Offline caching NOT allow for the share"},
+       {0, NULL}
+};
+static const true_false_string tfs_connect_support_uniquefilename = {
+       "Client allow to cache share namespaces",
+       "Client NOT allow to cache share namespaces"
+};
+static const true_false_string tfs_connect_support_extended_signature = {
+       "Extended signature",
+       "NOT extended signature"
+};
 
 static int
 dissect_connect_support_bits(tvbuff_t *tvb, proto_tree *parent_tree, int offset)
@@ -7283,6 +7527,12 @@ dissect_connect_support_bits(tvbuff_t *tvb, proto_tree *parent_tree, int offset)
                        tvb, offset, 2, mask);
                proto_tree_add_boolean(tree, hf_smb_connect_support_in_dfs,
                        tvb, offset, 2, mask);
+               proto_tree_add_uint(tree, hf_smb_connect_support_csc_mask_vals,
+                       tvb, offset, 2, mask);
+               proto_tree_add_boolean(tree, hf_smb_connect_support_uniquefilename,
+                       tvb, offset, 2, mask);
+               proto_tree_add_boolean(tree, hf_smb_connect_support_extended_signature,
+                       tvb, offset, 2, mask);
        }
 
        offset += 2;
@@ -7295,6 +7545,16 @@ static const true_false_string tfs_disconnect_tid = {
        "Do NOT disconnect TID"
 };
 
+static const true_false_string tfs_extended_signature = {
+       "Extended Signature",
+       "NOT Extended Signature"
+};
+
+static const true_false_string tfs_extended_response = {
+       "Extended Response",
+       "NOT Extended Response"
+};
+
 static int
 dissect_connect_flags(tvbuff_t *tvb, proto_tree *parent_tree, int offset)
 {
@@ -7311,6 +7571,10 @@ dissect_connect_flags(tvbuff_t *tvb, proto_tree *parent_tree, int offset)
 
                proto_tree_add_boolean(tree, hf_smb_connect_flags_dtid,
                        tvb, offset, 2, mask);
+               proto_tree_add_boolean(tree, hf_smb_connect_flags_ext_sig,
+                       tvb, offset, 2, mask);
+               proto_tree_add_boolean(tree, hf_smb_connect_flags_ext_resp,
+                       tvb, offset, 2, mask);
        }
 
        offset += 2;
@@ -7422,6 +7686,9 @@ dissect_tree_connect_andx_response(tvbuff_t *tvb, packet_info *pinfo, proto_tree
        guint16 andxoffset=0;
        guint16 bc;
        int an_len;
+       int count = 0;
+       proto_item *it = NULL;
+       proto_tree *tr = NULL;
        const char *an;
        smb_info_t *si = pinfo->private_data;
 
@@ -7465,11 +7732,27 @@ dissect_tree_connect_andx_response(tvbuff_t *tvb, packet_info *pinfo, proto_tree
           contains connect support bits, which looks plausible
           from the values I've seen. */
 
+       /* MaximalShareAccessRights and GuestMaximalShareAccessRights */
        while (wleft != 0) {
-               proto_tree_add_text(tree, tvb, offset, 2,
-                   "Word parameter: 0x%04x", tvb_get_letohs(tvb, offset));
-               offset += 2;
-               wleft--;
+               /*
+                * Refer to [MS-SMB] - v20100711
+                * When a server returns extended information, the response
+                * takes the following format, with WordCount = 7.
+                * MaximalShareAccessRights, and GuestMaximalShareAccessRights fields
+                * has added.
+                */
+               if (count == 0) {
+                       it = proto_tree_add_text(tree, tvb, offset, 4,
+                               "Maximal Share Access Rights");
+               } else {
+                       it = proto_tree_add_text(tree, tvb, offset, 4,
+                               "Guest Maximal Share Access Rights");
+               }
+               tr = proto_item_add_subtree(it, ett_smb_nt_access_mask);
+
+               offset = dissect_smb_access_mask(tvb, tr, offset);
+               wleft -= 2;
+               count++;
        }
 
        BYTE_COUNT;
@@ -7560,7 +7843,7 @@ dissect_tree_connect_andx_response(tvbuff_t *tvb, packet_info *pinfo, proto_tree
 #define NT_TRANS_QSD           6
 #define NT_TRANS_GET_USER_QUOTA        7
 #define NT_TRANS_SET_USER_QUOTA 8
-const value_string nt_cmd_vals[] = {
+static const value_string nt_cmd_vals[] = {
        {NT_TRANS_CREATE,               "NT CREATE"},
        {NT_TRANS_IOCTL,                "NT IOCTL"},
        {NT_TRANS_SSD,                  "NT SET SECURITY DESC"},
@@ -7572,6 +7855,8 @@ const value_string nt_cmd_vals[] = {
        {0, NULL}
 };
 
+value_string_ext nt_cmd_vals_ext = VALUE_STRING_EXT_INIT(nt_cmd_vals);
+
 static const value_string nt_ioctl_isfsctl_vals[] = {
        {0,     "Device IOCTL"},
        {1,     "FS control : FSCTL"},
@@ -8200,7 +8485,7 @@ dissect_nt_trans_data_request(tvbuff_t *tvb, packet_info *pinfo, int offset, pro
                tvb_ensure_bytes_exist(tvb, offset, bc);
                item = proto_tree_add_text(parent_tree, tvb, offset, bc,
                                "%s Data",
-                               val_to_str(ntd->subcmd, nt_cmd_vals, "Unknown NT transaction (%u)"));
+                               val_to_str_ext(ntd->subcmd, &nt_cmd_vals_ext, "Unknown NT transaction (%u)"));
                tree = proto_item_add_subtree(item, ett_smb_nt_trans_data);
        }
 
@@ -8223,8 +8508,9 @@ dissect_nt_trans_data_request(tvbuff_t *tvb, packet_info *pinfo, int offset, pro
        case NT_TRANS_IOCTL:
                /* ioctl data */
                ioctl_tvb=tvb_new_subset(tvb, offset, MIN((int)bc, tvb_length_remaining(tvb, offset)), bc);
-               dissect_smb2_ioctl_data(ioctl_tvb, pinfo, tree, top_tree, nti->ioctl_function, TRUE);
-
+               if (nti){
+                       dissect_smb2_ioctl_data(ioctl_tvb, pinfo, tree, top_tree_global, nti->ioctl_function, TRUE);
+               }
 
                offset += bc;
 
@@ -8284,7 +8570,7 @@ dissect_nt_trans_param_request(tvbuff_t *tvb, packet_info *pinfo, int offset, pr
        proto_item *item = NULL;
        proto_tree *tree = NULL;
        smb_info_t *si;
-       guint32 fn_len, create_flags, access_mask, file_attributes, share_access, create_options, create_disposition;
+       guint32 fn_len, create_flags, access_mask, share_access, create_options, create_disposition;
        const char *fn;
 
        si = (smb_info_t *)pinfo->private_data;
@@ -8294,7 +8580,7 @@ dissect_nt_trans_param_request(tvbuff_t *tvb, packet_info *pinfo, int offset, pr
        if(parent_tree){
                item = proto_tree_add_text(parent_tree, tvb, offset, len,
                                "%s Parameters",
-                               val_to_str(ntd->subcmd, nt_cmd_vals, "Unknown NT transaction (%u)"));
+                               val_to_str_ext(ntd->subcmd, &nt_cmd_vals_ext, "Unknown NT transaction (%u)"));
                tree = proto_item_add_subtree(item, ett_smb_nt_trans_param);
        }
 
@@ -8319,8 +8605,7 @@ dissect_nt_trans_param_request(tvbuff_t *tvb, packet_info *pinfo, int offset, pr
                COUNT_BYTES(8);
 
                /* Extended File Attributes */
-               file_attributes=tvb_get_letohl(tvb, offset);
-               offset = dissect_file_ext_attr_bits(tvb, tree, offset, 4, file_attributes);
+               offset = dissect_file_ext_attr(tvb, tree, offset);
                bc -= 4;
 
                /* share access */
@@ -8443,22 +8728,22 @@ dissect_nt_trans_setup_request(tvbuff_t *tvb, packet_info *pinfo, int offset, pr
        proto_tree *tree = NULL;
        int old_offset = offset;
        smb_info_t *si;
-       smb_nt_transact_info_t *nti;
+       smb_nt_transact_info_t *nti = NULL;
        smb_saved_info_t *sip;
 
 
        si = (smb_info_t *)pinfo->private_data;
        DISSECTOR_ASSERT(si);
        sip = si->sip;
-       DISSECTOR_ASSERT(sip);
-       nti=sip->extra_info;
-
+       if (sip && sip->extra_info_type == SMB_EI_NTI) {
+               nti=sip->extra_info;
+       }
 
        if(parent_tree){
                tvb_ensure_bytes_exist(tvb, offset, len);
                item = proto_tree_add_text(parent_tree, tvb, offset, len,
                                "%s Setup",
-                               val_to_str(ntd->subcmd, nt_cmd_vals, "Unknown NT transaction (%u)"));
+                               val_to_str_ext(ntd->subcmd, &nt_cmd_vals_ext, "Unknown NT transaction (%u)"));
                tree = proto_item_add_subtree(item, ett_smb_nt_trans_setup);
        }
 
@@ -8469,7 +8754,7 @@ dissect_nt_trans_setup_request(tvbuff_t *tvb, packet_info *pinfo, int offset, pr
                guint16 fid;
 
                /* function code */
-               offset = dissect_smb2_ioctl_function(tvb, pinfo, tree, offset, &nti->ioctl_function);
+               offset = dissect_smb2_ioctl_function(tvb, pinfo, tree, offset, nti ? &nti->ioctl_function : NULL);
 
                /* fid */
                fid = tvb_get_letohs(tvb, offset);
@@ -8642,7 +8927,7 @@ dissect_nt_transaction_request(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree
                proto_tree_add_uint(tree, hf_smb_nt_trans_subcmd, tvb, offset, 2, subcmd);
                if(check_col(pinfo->cinfo, COL_INFO)){
                        col_append_fstr(pinfo->cinfo, COL_INFO, ", %s",
-                               val_to_str(subcmd, nt_cmd_vals, "<unknown>"));
+                               val_to_str_ext(subcmd, &nt_cmd_vals_ext, "<unknown>"));
                }
                ntd.subcmd = subcmd;
                if (!si->unidir && sip) {
@@ -8745,7 +9030,7 @@ dissect_nt_trans_data_response(tvbuff_t *tvb, packet_info *pinfo,
                if(nti != NULL){
                        item = proto_tree_add_text(parent_tree, tvb, offset, len,
                                "%s Data",
-                               val_to_str(nti->subcmd, nt_cmd_vals, "Unknown NT Transaction (%u)"));
+                               val_to_str_ext(nti->subcmd, &nt_cmd_vals_ext, "Unknown NT Transaction (%u)"));
                } else {
                        /*
                         * We never saw the request to which this is a
@@ -8767,7 +9052,7 @@ dissect_nt_trans_data_response(tvbuff_t *tvb, packet_info *pinfo,
        case NT_TRANS_IOCTL:
                /* ioctl data */
                ioctl_tvb=tvb_new_subset(tvb, offset, MIN((int)len, tvb_length_remaining(tvb, offset)), len);
-               dissect_smb2_ioctl_data(ioctl_tvb, pinfo, tree, top_tree, nti->ioctl_function, FALSE);
+               dissect_smb2_ioctl_data(ioctl_tvb, pinfo, tree, top_tree_global, nti->ioctl_function, FALSE);
 
                offset += len;
 
@@ -8837,7 +9122,7 @@ dissect_nt_trans_param_response(tvbuff_t *tvb, packet_info *pinfo,
                if(nti != NULL){
                        item = proto_tree_add_text(parent_tree, tvb, offset, len,
                                "%s Parameters",
-                               val_to_str(nti->subcmd, nt_cmd_vals, "Unknown NT Transaction (%u)"));
+                               val_to_str_ext(nti->subcmd, &nt_cmd_vals_ext, "Unknown NT Transaction (%u)"));
                } else {
                        /*
                         * We never saw the request to which this is a
@@ -9049,7 +9334,7 @@ dissect_nt_trans_setup_response(tvbuff_t *tvb, packet_info *pinfo,
                if(nti != NULL){
                        item = proto_tree_add_text(parent_tree, tvb, offset, len,
                                "%s Setup",
-                               val_to_str(nti->subcmd, nt_cmd_vals, "Unknown NT Transaction (%u)"));
+                               val_to_str_ext(nti->subcmd, &nt_cmd_vals_ext, "Unknown NT Transaction (%u)"));
                } else {
                        /*
                         * We never saw the request to which this is a
@@ -9118,7 +9403,7 @@ dissect_nt_transaction_response(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tre
                proto_tree_add_uint(tree, hf_smb_nt_trans_subcmd, tvb, 0, 0, nti->subcmd);
                if(check_col(pinfo->cinfo, COL_INFO)){
                        col_append_fstr(pinfo->cinfo, COL_INFO, ", %s",
-                               val_to_str(nti->subcmd, nt_cmd_vals, "<unknown (%u)>"));
+                               val_to_str_ext(nti->subcmd, &nt_cmd_vals_ext, "<unknown (%u)>"));
                }
        } else {
                proto_tree_add_text(tree, tvb, offset, 0,
@@ -9910,6 +10195,8 @@ dissect_nt_create_andx_response(tvbuff_t *tvb, packet_info *pinfo, proto_tree *t
        offset += 8;
 
        /* end of file */
+        /* We store the end of file */
+        fid_info->end_of_file=tvb_get_letoh64(tvb, offset);
        proto_tree_add_item(tree, hf_smb_end_of_file, tvb, offset, 8, TRUE);
        offset += 8;
 
@@ -9985,7 +10272,7 @@ dissect_nt_cancel_request(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *tre
    XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX */
 
 
-const value_string trans2_cmd_vals[] = {
+static const value_string trans2_cmd_vals[] = {
        { 0x00,         "OPEN2" },
        { 0x01,         "FIND_FIRST2" },
        { 0x02,         "FIND_NEXT2" },
@@ -10001,11 +10288,14 @@ const value_string trans2_cmd_vals[] = {
        { 0x0C,         "FIND_NOTIFY_NEXT" },
        { 0x0D,         "CREATE_DIRECTORY" },
        { 0x0E,         "SESSION_SETUP" },
+        { 0x0F,         "Unknown (0x0f)" },  /* dummy so val_to_str_ext can do indexed lookup */
        { 0x10,         "GET_DFS_REFERRAL" },
        { 0x11,         "REPORT_DFS_INCONSISTENCY" },
        { 0,    NULL }
 };
 
+value_string_ext trans2_cmd_vals_ext = VALUE_STRING_EXT_INIT(trans2_cmd_vals);
+
 static const true_false_string tfs_tf_dtid = {
        "Also DISCONNECT TID",
        "Do NOT disconnect TID"
@@ -10047,6 +10337,8 @@ static const value_string ff2_il_vals[] = {
        { 0x0102,       "Find File Full Directory Info"},
        { 0x0103,       "Find File Names Info"},
        { 0x0104,       "Find File Both Directory Info"},
+       { 0x0105,       "Find File Full Directory Info"},
+       { 0x0106,       "Find File Id Both Directory Info"},
        { 0x0202,       "Find File UNIX"},
        {0, NULL}
 };
@@ -10419,8 +10711,8 @@ dissect_transaction2_request_parameters(tvbuff_t *tvb, packet_info *pinfo,
                tvb_ensure_bytes_exist(tvb, offset, bc);
                item = proto_tree_add_text(parent_tree, tvb, offset, bc,
                                "%s Parameters",
-                               val_to_str(subcmd, trans2_cmd_vals,
-                                          "Unknown (0x%02x)"));
+                               val_to_str_ext(subcmd, &trans2_cmd_vals_ext,
+                                              "Unknown (0x%02x)"));
                tree = proto_item_add_subtree(item, ett_smb_transaction_params);
        }
 
@@ -10443,7 +10735,7 @@ dissect_transaction2_request_parameters(tvbuff_t *tvb, packet_info *pinfo,
 
                /* File Attributes */
                CHECK_BYTE_COUNT_TRANS(2);
-               offset = dissect_file_attributes(tvb, tree, offset, 2);
+               offset = dissect_file_attributes(tvb, tree, offset);
                bc -= 2;
 
                /* create time */
@@ -11245,7 +11537,7 @@ dissect_get_dfs_referral_data(tvbuff_t *tvb, packet_info *pinfo,
                while(numref--){
                        proto_item *ri = NULL;
                        proto_tree *rt = NULL;
-                       int old_offset=offset;
+                       int old_offset_2=offset;
                        guint16 version;
 
                        if(tree){
@@ -11292,17 +11584,17 @@ dissect_get_dfs_referral_data(tvbuff_t *tvb, packet_info *pinfo,
                                break;
 
                        case 2:
-                               offset = dissect_dfs_referral_entry_v2(tvb, rt, old_offset, offset,
+                               offset = dissect_dfs_referral_entry_v2(tvb, rt, old_offset_2, offset,
                                                                       refflags, bcp, si->unicode, &ucstring_end);
                                break;
                        case 3:
-                               offset = dissect_dfs_referral_entry_v3(tvb, rt, old_offset, offset,
+                               offset = dissect_dfs_referral_entry_v3(tvb, rt, old_offset_2, offset,
                                                                       refflags, bcp, si->unicode, &ucstring_end);
                                break;
                        case 4:
                                /* V4 is extactly same as V3, except the version number and
                                 * one more ReferralEntryFlags */
-                               offset = dissect_dfs_referral_entry_v3(tvb, rt, old_offset, offset,
+                               offset = dissect_dfs_referral_entry_v3(tvb, rt, old_offset_2, offset,
                                                                       refflags, bcp, si->unicode, &ucstring_end);
                                break;
                        }
@@ -11311,7 +11603,7 @@ dissect_get_dfs_referral_data(tvbuff_t *tvb, packet_info *pinfo,
                         * Show anything beyond the length of the referral
                         * as unknown data.
                         */
-                       unklen = (old_offset + refsize) - offset;
+                       unklen = (old_offset_2 + refsize) - offset;
                        if (unklen < 0) {
                                /*
                                 * XXX - the length is bogus.
@@ -11325,7 +11617,7 @@ dissect_get_dfs_referral_data(tvbuff_t *tvb, packet_info *pinfo,
                                COUNT_BYTES_TRANS_SUBR(unklen);
                        }
 
-                       proto_item_set_len(ri, offset-old_offset);
+                       proto_item_set_len(ri, offset-old_offset_2);
                }
 
                /*
@@ -11418,7 +11710,7 @@ dissect_4_2_16_1(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *tree,
 
        /* File Attributes */
        CHECK_BYTE_COUNT_SUBR(2);
-       offset = dissect_file_attributes(tvb, tree, offset, 2);
+       offset = dissect_file_attributes(tvb, tree, offset);
        *bcp -= 2;
 
        /* ea length */
@@ -11544,7 +11836,7 @@ dissect_4_2_16_4(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *tree,
 
        /* File Attributes */
        CHECK_BYTE_COUNT_SUBR(4);
-       offset = dissect_file_attributes(tvb, tree, offset, 4);
+       offset = dissect_file_ext_attr(tvb, tree, offset);
        *bcp -= 4;
 
        *trunc = FALSE;
@@ -11746,7 +12038,7 @@ dissect_qfi_SMB_FILE_ALL_INFO(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tre
 
        /* File Attributes */
        CHECK_BYTE_COUNT_SUBR(4);
-       offset = dissect_file_attributes(tvb, tree, offset, 4);
+       offset = dissect_file_ext_attr(tvb, tree, offset);
        *bcp -= 4;
 
        /* 4 pad bytes */
@@ -12237,7 +12529,7 @@ dissect_qfi_SMB_FILE_NETWORK_OPEN_INFO(tvbuff_t *tvb,
 
        /* File Attributes */
        CHECK_BYTE_COUNT_SUBR(4);
-       offset = dissect_file_attributes(tvb, tree, offset, 4);
+       offset = dissect_file_ext_attr(tvb, tree, offset);
        *bcp -= 4;
 
         /* Unknown, possibly count of network accessors ... */
@@ -12755,8 +13047,8 @@ dissect_transaction2_request_data(tvbuff_t *tvb, packet_info *pinfo,
                tvb_ensure_bytes_exist(tvb, offset, dc);
                item = proto_tree_add_text(parent_tree, tvb, offset, dc,
                                "%s Data",
-                               val_to_str(subcmd, trans2_cmd_vals,
-                                               "Unknown (0x%02x)"));
+                               val_to_str_ext(subcmd, &trans2_cmd_vals_ext,
+                                              "Unknown (0x%02x)"));
                tree = proto_item_add_subtree(item, ett_smb_transaction_data);
        }
 
@@ -13102,8 +13394,8 @@ dissect_transaction_request(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
                                    tvb, offset, 2, subcmd);
                                if (check_col(pinfo->cinfo, COL_INFO)) {
                                        col_append_fstr(pinfo->cinfo, COL_INFO, ", %s",
-                                           val_to_str(subcmd, trans2_cmd_vals,
-                                               "Unknown (0x%02x)"));
+                                           val_to_str_ext(subcmd, &trans2_cmd_vals_ext,
+                                                          "Unknown (0x%02x)"));
                                }
                                if (!si->unidir) {
                                        if(!pinfo->fd->flags.visited && si->sip){
@@ -13313,7 +13605,7 @@ dissect_transaction_request(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
 
                                dissected_trans = dissect_pipe_smb(sp_tvb,
                                    s_tvb, pd_tvb, p_tvb, d_tvb, an+6, pinfo,
-                                   top_tree);
+                                   top_tree_global);
 
                                /* In case we did not see the TreeConnect call,
                                   store this TID here as well as a IPC TID
@@ -13334,7 +13626,7 @@ dissect_transaction_request(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
                                 */
                                sp_tvb = tvb_new_subset(tvb, spo, spc, spc);
                                dissected_trans = dissect_mailslot_smb(sp_tvb,
-                                   s_tvb, d_tvb, an+10, pinfo, top_tree);
+                                   s_tvb, d_tvb, an+10, pinfo, top_tree_global);
                        }
                        if (!dissected_trans)
                                dissect_trans_data(s_tvb, p_tvb, d_tvb, tree);
@@ -13420,7 +13712,7 @@ dissect_4_3_4_1(tvbuff_t *tvb, packet_info *pinfo, proto_tree *parent_tree,
 
        /* File Attributes */
        CHECK_BYTE_COUNT_SUBR(2);
-       offset = dissect_file_attributes(tvb, tree, offset, 2);
+       offset = dissect_file_attributes(tvb, tree, offset);
        *bcp -= 2;
 
        /* file name len */
@@ -13521,7 +13813,7 @@ dissect_4_3_4_2(tvbuff_t *tvb, packet_info *pinfo, proto_tree *parent_tree,
 
        /* File Attributes */
        CHECK_BYTE_COUNT_SUBR(2);
-       offset = dissect_file_attributes(tvb, tree, offset, 2);
+       offset = dissect_file_attributes(tvb, tree, offset);
        *bcp -= 2;
 
        /* ea length */
@@ -13893,6 +14185,267 @@ dissect_4_3_4_6(tvbuff_t *tvb, packet_info *pinfo, proto_tree *parent_tree,
        return offset;
 }
 
+static int
+dissect_4_3_4_6full(tvbuff_t *tvb, packet_info *pinfo, proto_tree *parent_tree,
+    int offset, guint16 *bcp, gboolean *trunc)
+{
+       int fn_len;
+       const char *fn;
+       int old_offset = offset;
+       proto_item *item = NULL;
+       proto_tree *tree = NULL;
+       smb_info_t *si;
+       guint32 neo;
+       int padcnt;
+
+       si = (smb_info_t *)pinfo->private_data;
+       DISSECTOR_ASSERT(si);
+
+       if(parent_tree){
+               tvb_ensure_bytes_exist(tvb, offset, *bcp);
+               item = proto_tree_add_text(parent_tree, tvb, offset, *bcp, "%s",
+                   val_to_str(si->info_level, ff2_il_vals, "Unknown (0x%02x)"));
+               tree = proto_item_add_subtree(item, ett_smb_ff2_data);
+       }
+
+       /*
+        * XXX - I have not seen any of these that contain a resume
+        * key, even though some of the requests had the "return resume
+        * key" flag set.
+        */
+
+       /* next entry offset */
+       CHECK_BYTE_COUNT_SUBR(4);
+       neo = tvb_get_letohl(tvb, offset);
+       proto_tree_add_uint(tree, hf_smb_next_entry_offset, tvb, offset, 4, neo);
+       COUNT_BYTES_SUBR(4);
+
+       /* file index */
+       CHECK_BYTE_COUNT_SUBR(4);
+       proto_tree_add_item(tree, hf_smb_file_index, tvb, offset, 4, TRUE);
+       COUNT_BYTES_SUBR(4);
+
+        /* dissect standard 8-byte timestamps */
+       offset = dissect_smb_standard_8byte_timestamps(tvb, pinfo, tree, offset, bcp, trunc);
+       if (*trunc) {
+         return offset;
+       }
+
+       /* end of file */
+       CHECK_BYTE_COUNT_SUBR(8);
+       proto_tree_add_item(tree, hf_smb_end_of_file, tvb, offset, 8, TRUE);
+       COUNT_BYTES_SUBR(8);
+
+       /* allocation size */
+       CHECK_BYTE_COUNT_SUBR(8);
+       proto_tree_add_item(tree, hf_smb_alloc_size64, tvb, offset, 8, TRUE);
+       COUNT_BYTES_SUBR(8);
+
+       /* Extended File Attributes */
+       CHECK_BYTE_COUNT_SUBR(4);
+       offset = dissect_file_ext_attr(tvb, tree, offset);
+       *bcp -= 4;
+
+       /* file name len */
+       CHECK_BYTE_COUNT_SUBR(4);
+       fn_len = tvb_get_letohl(tvb, offset);
+       proto_tree_add_uint(tree, hf_smb_file_name_len, tvb, offset, 4, fn_len);
+       COUNT_BYTES_SUBR(4);
+
+       /*
+        * EA length.
+        *
+        * XXX - in one captures, this has the topmost bit set, and the
+        * rest of the bits have the value 7.  Is the topmost bit being
+        * set some indication that the value *isn't* the length of
+        * the EAs?
+        */
+       CHECK_BYTE_COUNT_SUBR(4);
+       proto_tree_add_item(tree, hf_smb_ea_list_length, tvb, offset, 4, TRUE);
+       COUNT_BYTES_SUBR(4);
+
+       /* skip 4 bytes */
+       COUNT_BYTES_SUBR(4);
+
+       CHECK_BYTE_COUNT_SUBR(8);
+       proto_tree_add_item(tree, hf_smb_index_number, tvb, offset, 8, TRUE);
+       COUNT_BYTES_SUBR(8);
+
+       /* file name */
+       fn = get_unicode_or_ascii_string(tvb, &offset, si->unicode, &fn_len, FALSE, TRUE, bcp);
+       CHECK_STRING_SUBR(fn);
+       proto_tree_add_string(tree, hf_smb_file_name, tvb, offset, fn_len,
+               fn);
+       COUNT_BYTES_SUBR(fn_len);
+
+       if (check_col(pinfo->cinfo, COL_INFO)) {
+               col_append_fstr(pinfo->cinfo, COL_INFO, " %s",
+                   format_text(fn, strlen(fn)));
+       }
+
+       /* skip to next structure */
+       if(neo){
+               padcnt = (old_offset + neo) - offset;
+               if (padcnt < 0) {
+                       /*
+                        * XXX - this is bogus; flag it?
+                        */
+                       padcnt = 0;
+               }
+               if (padcnt != 0) {
+                       CHECK_BYTE_COUNT_SUBR(padcnt);
+                       COUNT_BYTES_SUBR(padcnt);
+               }
+       }
+
+       proto_item_append_text(item, " File: %s", format_text(fn, strlen(fn)));
+       proto_item_set_len(item, offset-old_offset);
+
+       *trunc = FALSE;
+       return offset;
+}
+
+static int
+dissect_4_3_4_6_id_both(tvbuff_t *tvb, packet_info *pinfo, proto_tree *parent_tree,
+    int offset, guint16 *bcp, gboolean *trunc)
+{
+       int fn_len, sfn_len;
+       const char *fn, *sfn;
+       int old_offset = offset;
+       proto_item *item = NULL;
+       proto_tree *tree = NULL;
+       smb_info_t *si;
+       guint32 neo;
+       int padcnt;
+
+       si = (smb_info_t *)pinfo->private_data;
+       DISSECTOR_ASSERT(si);
+
+       if(parent_tree){
+               tvb_ensure_bytes_exist(tvb, offset, *bcp);
+               item = proto_tree_add_text(parent_tree, tvb, offset, *bcp, "%s",
+                   val_to_str(si->info_level, ff2_il_vals, "Unknown (0x%02x)"));
+               tree = proto_item_add_subtree(item, ett_smb_ff2_data);
+       }
+
+       /*
+        * XXX - I have not seen any of these that contain a resume
+        * key, even though some of the requests had the "return resume
+        * key" flag set.
+        */
+
+       /* next entry offset */
+       CHECK_BYTE_COUNT_SUBR(4);
+       neo = tvb_get_letohl(tvb, offset);
+       proto_tree_add_uint(tree, hf_smb_next_entry_offset, tvb, offset, 4, neo);
+       COUNT_BYTES_SUBR(4);
+
+       /* file index */
+       CHECK_BYTE_COUNT_SUBR(4);
+       proto_tree_add_item(tree, hf_smb_file_index, tvb, offset, 4, TRUE);
+       COUNT_BYTES_SUBR(4);
+
+        /* dissect standard 8-byte timestamps */
+       offset = dissect_smb_standard_8byte_timestamps(tvb, pinfo, tree, offset, bcp, trunc);
+       if (*trunc) {
+         return offset;
+       }
+
+       /* end of file */
+       CHECK_BYTE_COUNT_SUBR(8);
+       proto_tree_add_item(tree, hf_smb_end_of_file, tvb, offset, 8, TRUE);
+       COUNT_BYTES_SUBR(8);
+
+       /* allocation size */
+       CHECK_BYTE_COUNT_SUBR(8);
+       proto_tree_add_item(tree, hf_smb_alloc_size64, tvb, offset, 8, TRUE);
+       COUNT_BYTES_SUBR(8);
+
+       /* Extended File Attributes */
+       CHECK_BYTE_COUNT_SUBR(4);
+       offset = dissect_file_ext_attr(tvb, tree, offset);
+       *bcp -= 4;
+
+       /* file name len */
+       CHECK_BYTE_COUNT_SUBR(4);
+       fn_len = tvb_get_letohl(tvb, offset);
+       proto_tree_add_uint(tree, hf_smb_file_name_len, tvb, offset, 4, fn_len);
+       COUNT_BYTES_SUBR(4);
+
+       /*
+        * EA length.
+        *
+        * XXX - in one captures, this has the topmost bit set, and the
+        * rest of the bits have the value 7.  Is the topmost bit being
+        * set some indication that the value *isn't* the length of
+        * the EAs?
+        */
+       CHECK_BYTE_COUNT_SUBR(4);
+       proto_tree_add_item(tree, hf_smb_ea_list_length, tvb, offset, 4, TRUE);
+       COUNT_BYTES_SUBR(4);
+
+       /* short file name len */
+       CHECK_BYTE_COUNT_SUBR(1);
+       sfn_len = tvb_get_guint8(tvb, offset);
+       proto_tree_add_uint(tree, hf_smb_short_file_name_len, tvb, offset, 1, sfn_len);
+       COUNT_BYTES_SUBR(1);
+
+       /* reserved byte */
+       CHECK_BYTE_COUNT_SUBR(1);
+       proto_tree_add_item(tree, hf_smb_reserved, tvb, offset, 1, TRUE);
+       COUNT_BYTES_SUBR(1);
+
+       /* short file name - it's not always in Unicode */
+       sfn = get_unicode_or_ascii_string(tvb, &offset, si->unicode, &sfn_len, FALSE, TRUE, bcp);
+       CHECK_STRING_SUBR(sfn);
+       proto_tree_add_string(tree, hf_smb_short_file_name, tvb, offset, 24,
+               sfn);
+       COUNT_BYTES_SUBR(24);
+
+       /* reserved bytes */
+       CHECK_BYTE_COUNT_SUBR(2);
+       proto_tree_add_item(tree, hf_smb_reserved, tvb, offset, 2, TRUE);
+       COUNT_BYTES_SUBR(2);
+
+       /* file id */
+       CHECK_BYTE_COUNT_SUBR(8);
+       proto_tree_add_item(tree, hf_smb_index_number, tvb, offset, 8, TRUE);
+       COUNT_BYTES_SUBR(8);
+
+       /* file name */
+       fn = get_unicode_or_ascii_string(tvb, &offset, si->unicode, &fn_len, FALSE, TRUE, bcp);
+       CHECK_STRING_SUBR(fn);
+       proto_tree_add_string(tree, hf_smb_file_name, tvb, offset, fn_len,
+               fn);
+       COUNT_BYTES_SUBR(fn_len);
+
+       if (check_col(pinfo->cinfo, COL_INFO)) {
+               col_append_fstr(pinfo->cinfo, COL_INFO, " %s",
+                   format_text(fn, strlen(fn)));
+       }
+
+       /* skip to next structure */
+       if(neo){
+               padcnt = (old_offset + neo) - offset;
+               if (padcnt < 0) {
+                       /*
+                        * XXX - this is bogus; flag it?
+                        */
+                       padcnt = 0;
+               }
+               if (padcnt != 0) {
+                       CHECK_BYTE_COUNT_SUBR(padcnt);
+                       COUNT_BYTES_SUBR(padcnt);
+               }
+       }
+
+       proto_item_append_text(item, " File: %s", format_text(fn, strlen(fn)));
+       proto_item_set_len(item, offset-old_offset);
+
+       *trunc = FALSE;
+       return offset;
+}
+
 static int
 dissect_4_3_4_7(tvbuff_t *tvb, packet_info *pinfo, proto_tree *parent_tree,
     int offset, guint16 *bcp, gboolean *trunc)
@@ -14123,6 +14676,14 @@ dissect_ff2_response_data(tvbuff_t * tvb, packet_info * pinfo,
                offset = dissect_4_3_4_6(tvb, pinfo, tree, offset, bcp,
                    trunc);
                break;
+       case 0x0105:    /*Find File Full Directory Info*/
+               offset = dissect_4_3_4_6full(tvb, pinfo, tree, offset, bcp,
+                   trunc);
+               break;
+       case 0x0106:    /*Find File Id Both Directory Info*/
+               offset = dissect_4_3_4_6_id_both(tvb, pinfo, tree, offset, bcp,
+                   trunc);
+               break;
        case 0x0202:    /*Find File UNIX*/
                offset = dissect_4_3_4_8(tvb, pinfo, tree, offset, bcp,
                    trunc);
@@ -14519,7 +15080,7 @@ dissect_qfsi_vals(tvbuff_t * tvb, packet_info * pinfo, proto_tree * tree,
                offset = dissect_qfsi_FS_ATTRIBUTE_INFO(tvb, pinfo, tree, offset, bcp, si->unicode);
                break;
        case 0x200: {   /* SMB_QUERY_CIFS_UNIX_INFO */
-               proto_item *item = NULL;
+               proto_item *item_2 = NULL;
                proto_tree *subtree = NULL;
                guint32 caps_lo, caps_hi;
 
@@ -14541,11 +15102,11 @@ dissect_qfsi_vals(tvbuff_t * tvb, packet_info * pinfo, proto_tree * tree,
                caps_hi = tvb_get_letohl(tvb, offset + 4);
 
                if (tree) {
-                       item = proto_tree_add_text(
+                       item_2 = proto_tree_add_text(
                                tree, tvb, offset, 8, "Capabilities: 0x%08x%08x",
                                caps_hi, caps_lo);
                        subtree = proto_item_add_subtree(
-                               item, ett_smb_unix_capabilities);
+                               item_2, ett_smb_unix_capabilities);
                }
 
                proto_tree_add_boolean(
@@ -14619,7 +15180,7 @@ dissect_qfsi_vals(tvbuff_t * tvb, packet_info * pinfo, proto_tree * tree,
                COUNT_BYTES_TRANS_SUBR(4);
                /* Mac Support Flags */
                CHECK_BYTE_COUNT_TRANS_SUBR(4);
-               support = tvb_get_ntohl(tvb, offset);
+               support = tvb_get_letohl(tvb, offset);
                item = proto_tree_add_text(tree, tvb, offset, 4,
                                           "Mac Support Flags: 0x%08x", support);
                ti = proto_item_add_subtree(item, ett_smb_mac_support_flags);
@@ -14677,8 +15238,8 @@ dissect_transaction2_response_data(tvbuff_t *tvb, packet_info *pinfo,
                if (t2i != NULL && t2i->subcmd != -1) {
                        item = proto_tree_add_text(parent_tree, tvb, offset, dc,
                                "%s Data",
-                               val_to_str(t2i->subcmd, trans2_cmd_vals,
-                                       "Unknown (0x%02x)"));
+                               val_to_str_ext(t2i->subcmd, &trans2_cmd_vals_ext,
+                                              "Unknown (0x%02x)"));
                        tree = proto_item_add_subtree(item, ett_smb_transaction_data);
                } else {
                        item = proto_tree_add_text(parent_tree, tvb, offset, dc,
@@ -14852,8 +15413,8 @@ dissect_transaction2_response_parameters(tvbuff_t *tvb, packet_info *pinfo, prot
                if (t2i != NULL && t2i->subcmd != -1) {
                        item = proto_tree_add_text(parent_tree, tvb, offset, pc,
                                "%s Parameters",
-                               val_to_str(t2i->subcmd, trans2_cmd_vals,
-                                               "Unknown (0x%02x)"));
+                               val_to_str_ext(t2i->subcmd, &trans2_cmd_vals_ext,
+                                              "Unknown (0x%02x)"));
                        tree = proto_item_add_subtree(item, ett_smb_transaction_params);
                } else {
                        item = proto_tree_add_text(parent_tree, tvb, offset, pc,
@@ -14887,7 +15448,7 @@ dissect_transaction2_response_parameters(tvbuff_t *tvb, packet_info *pinfo, prot
                 */
 
                /* File Attributes */
-               offset = dissect_file_attributes(tvb, tree, offset, 2);
+               offset = dissect_file_attributes(tvb, tree, offset);
 
                /* create time */
                offset = dissect_smb_datetime(tvb, tree, offset,
@@ -15166,9 +15727,9 @@ dissect_transaction_response(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *
 
                                if (t2i && check_col(pinfo->cinfo, COL_INFO)) {
                                        col_append_fstr(pinfo->cinfo, COL_INFO, ", %s",
-                                               val_to_str(t2i->subcmd,
-                                                       trans2_cmd_vals,
-                                                       "<unknown (0x%02x)>"));
+                                               val_to_str_ext(t2i->subcmd,
+                                                              &trans2_cmd_vals_ext,
+                                                              "<unknown (0x%02x)>"));
                                }
                        }
                }
@@ -15398,7 +15959,7 @@ dissect_transaction_response(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *
                                if( pd_tvb) {
                                        dissected_trans = dissect_pipe_smb(
                                                sp_tvb, s_tvb, pd_tvb, p_tvb,
-                                               d_tvb, NULL, pinfo, top_tree);
+                                               d_tvb, NULL, pinfo, top_tree_global);
                                }
                                break;
 
@@ -15409,7 +15970,7 @@ dissect_transaction_response(tvbuff_t *tvb, packet_info *pinfo _U_, proto_tree *
                                if(d_tvb){
                                        dissected_trans = dissect_mailslot_smb(
                                                sp_tvb, s_tvb, d_tvb, NULL, pinfo,
-                                               top_tree);
+                                               top_tree_global);
                                }
                                break;
                        }
@@ -15829,8 +16390,10 @@ dissect_smb_command(tvbuff_t *tvb, packet_info *pinfo, int offset, proto_tree *s
  * This means that this value_string array MUST always
  * 1, contain all entries 0x00 to 0xff
  * 2, all entries must be in order.
+ * Note: This value_string array can also be accessed directly via the use of value_string_ext
+ * ToDo?: use val_to_str_ext instead of decode_smb_name() ?
  */
-const value_string smb_cmd_vals[] = {
+static const value_string smb_cmd_vals[] = {
   { 0x00, "Create Directory" },
   { 0x01, "Delete Directory" },
   { 0x02, "Open" },
@@ -16090,6 +16653,8 @@ const value_string smb_cmd_vals[] = {
   { 0x00, NULL },
 };
 
+value_string_ext smb_cmd_vals_ext = VALUE_STRING_EXT_INIT(smb_cmd_vals);
+
 static const char *decode_smb_name(guint8 cmd)
 {
   return(smb_cmd_vals[cmd].strptr);
@@ -16396,7 +16961,7 @@ dissect_smb(tvbuff_t *tvb, packet_info *pinfo, proto_tree *parent_tree)
 
        si=ep_alloc0(sizeof(smb_info_t));
 
-       top_tree=parent_tree;
+       top_tree_global=parent_tree;
 
        col_set_str(pinfo->cinfo, COL_PROTOCOL, "SMB");
        col_clear(pinfo->cinfo, COL_INFO);
@@ -16443,13 +17008,7 @@ dissect_smb(tvbuff_t *tvb, packet_info *pinfo, proto_tree *parent_tree)
 
        /* find which conversation we are part of and get the tables for that
           conversation*/
-       conversation = find_conversation(pinfo->fd->num, &pinfo->src, &pinfo->dst,
-                pinfo->ptype,  pinfo->srcport, pinfo->destport, 0);
-       if(!conversation){
-               /* OK this is a new conversation so lets create it */
-               conversation = conversation_new(pinfo->fd->num, &pinfo->src, &pinfo->dst,
-                       pinfo->ptype, pinfo->srcport, pinfo->destport, 0);
-       }
+       conversation = find_or_create_conversation(pinfo);
        /* see if we already have the smb data for this conversation */
        si->ct=conversation_get_proto_data(conversation, proto_smb);
        if(!si->ct){
@@ -16469,6 +17028,8 @@ dissect_smb(tvbuff_t *tvb, packet_info *pinfo, proto_tree *parent_tree)
                si->ct->fid_tree=se_tree_create_non_persistent(EMEM_TREE_TYPE_RED_BLACK, "SMB fid_tree");
                si->ct->tid_tree=se_tree_create_non_persistent(EMEM_TREE_TYPE_RED_BLACK, "SMB tid_tree");
                si->ct->uid_tree=se_tree_create_non_persistent(EMEM_TREE_TYPE_RED_BLACK, "SMB uid_tree");
+                /* Initialize the GSL_fid_info for this ct */
+                si->ct->GSL_fid_info=NULL;
                conversation_add_proto_data(conversation, proto_smb, si->ct);
        }
 
@@ -16938,16 +17499,16 @@ proto_register_smb(void)
 {
        static hf_register_info hf[] = {
        { &hf_smb_cmd,
-               { "SMB Command", "smb.cmd", FT_UINT8, BASE_HEX,
-               VALS(smb_cmd_vals), 0x0, NULL, HFILL }},
+               { "SMB Command", "smb.cmd", FT_UINT8, BASE_HEX|BASE_EXT_STRING,
+               &smb_cmd_vals_ext, 0x0, NULL, HFILL }},
 
        { &hf_smb_trans2_subcmd,
-               { "Subcommand", "smb.trans2.cmd", FT_UINT16, BASE_HEX,
-               VALS(trans2_cmd_vals), 0, "Subcommand for TRANSACTION2", HFILL }},
+               { "Subcommand", "smb.trans2.cmd", FT_UINT16, BASE_HEX|BASE_EXT_STRING,
+               &trans2_cmd_vals_ext, 0, "Subcommand for TRANSACTION2", HFILL }},
 
        { &hf_smb_nt_trans_subcmd,
-               { "Function", "smb.nt.function", FT_UINT16, BASE_DEC,
-               VALS(nt_cmd_vals), 0, "Function for NT Transaction", HFILL }},
+               { "Function", "smb.nt.function", FT_UINT16, BASE_DEC|BASE_EXT_STRING,
+               &nt_cmd_vals_ext, 0, "Function for NT Transaction", HFILL }},
 
        { &hf_smb_word_count,
                { "Word Count (WCT)", "smb.wct", FT_UINT8, BASE_DEC,
@@ -17151,11 +17712,11 @@ proto_register_smb(void)
 
        { &hf_smb_security_blob_len,
                { "Security Blob Length", "smb.security_blob_len", FT_UINT16, BASE_DEC,
-               NULL, 0, "Security blob length", HFILL }},
+               NULL, 0, NULL, HFILL }},
 
        { &hf_smb_security_blob,
                { "Security Blob", "smb.security_blob", FT_BYTES, BASE_NONE,
-               NULL, 0, "Security blob", HFILL }},
+               NULL, 0, NULL, HFILL }},
 
        { &hf_smb_sm_mode16,
                { "Mode", "smb.sm.mode", FT_BOOLEAN, 16,
@@ -17190,7 +17751,7 @@ proto_register_smb(void)
                TFS(&tfs_rm_write), RAWMODE_WRITE, "Is Write Raw supported?", HFILL }},
 
        { &hf_smb_server_date_time,
-               { "Server Date and Time", "smb.server_date_time", FT_ABSOLUTE_TIME, BASE_NONE,
+               { "Server Date and Time", "smb.server_date_time", FT_ABSOLUTE_TIME, ABSOLUTE_TIME_LOCAL,
                NULL, 0, "Current date and time at server", HFILL }},
 
        { &hf_smb_server_smb_date,
@@ -17263,7 +17824,7 @@ proto_register_smb(void)
 
        { &hf_smb_server_cap_reserved,
                { "Reserved", "smb.server_cap.reserved", FT_BOOLEAN, 32,
-               TFS(&tfs_server_cap_reserved), SERVER_CAP_RESERVED, "RESERVED", HFILL }},
+               TFS(&tfs_server_cap_reserved), SERVER_CAP_RESERVED, NULL, HFILL }},
 
        { &hf_smb_server_cap_bulk_transfer,
                { "Bulk Transfer", "smb.server_cap.bulk_transfer", FT_BOOLEAN, 32,
@@ -17278,11 +17839,11 @@ proto_register_smb(void)
                TFS(&tfs_server_cap_extended_security), SERVER_CAP_EXTENDED_SECURITY, "Are Extended security exchanges supported?", HFILL }},
 
        { &hf_smb_system_time,
-               { "System Time", "smb.system.time", FT_ABSOLUTE_TIME, BASE_NONE,
+               { "System Time", "smb.system.time", FT_ABSOLUTE_TIME, ABSOLUTE_TIME_LOCAL,
                NULL, 0, NULL, HFILL }},
 
        { &hf_smb_unknown,
-               { "Unknown Data", "smb.unknown", FT_BYTES, BASE_NONE,
+               { "Unknown Data", "smb.unknown_data", FT_BYTES, BASE_NONE,
                NULL, 0, "Unknown Data. Should be implemented by someone", HFILL }},
 
        { &hf_smb_dir_name,
@@ -17530,15 +18091,15 @@ proto_register_smb(void)
                TFS(&tfs_da_writetru), 0x4000, "Writethrough mode?", HFILL }},
 
        { &hf_smb_create_time,
-               { "Created", "smb.create.time", FT_ABSOLUTE_TIME, BASE_NONE,
+               { "Created", "smb.create.time", FT_ABSOLUTE_TIME, ABSOLUTE_TIME_LOCAL,
                NULL, 0, "Creation Time", HFILL }},
 
        { &hf_smb_modify_time,
-               { "Modified", "smb.modify.time", FT_ABSOLUTE_TIME, BASE_NONE,
+               { "Modified", "smb.modify.time", FT_ABSOLUTE_TIME, ABSOLUTE_TIME_LOCAL,
                  NULL, 0, "Modification Time", HFILL }},
 
        { &hf_smb_backup_time,
-               { "Backed-up", "smb.backup.time", FT_ABSOLUTE_TIME, BASE_NONE,
+               { "Backed-up", "smb.backup.time", FT_ABSOLUTE_TIME, ABSOLUTE_TIME_LOCAL,
                  NULL, 0, "Backup time", HFILL}},
 
        { &hf_smb_mac_alloc_block_count,
@@ -17602,7 +18163,7 @@ proto_register_smb(void)
                NULL, 0, "Create Time, SMB_TIME format", HFILL }},
 
        { &hf_smb_last_write_time,
-               { "Last Write", "smb.last_write.time", FT_ABSOLUTE_TIME, BASE_NONE,
+               { "Last Write", "smb.last_write.time", FT_ABSOLUTE_TIME, ABSOLUTE_TIME_LOCAL,
                NULL, 0, "Time this file was last written to", HFILL }},
 
        { &hf_smb_last_write_dos_date,
@@ -17658,7 +18219,7 @@ proto_register_smb(void)
                VALS(seek_mode_vals), 0, "Seek Mode, what type of seek", HFILL }},
 
        { &hf_smb_access_time,
-               { "Last Access", "smb.access.time", FT_ABSOLUTE_TIME, BASE_NONE,
+               { "Last Access", "smb.access.time", FT_ABSOLUTE_TIME, ABSOLUTE_TIME_LOCAL,
                NULL, 0, "Last Access Time", HFILL }},
 
        { &hf_smb_access_dos_date,
@@ -17695,7 +18256,7 @@ proto_register_smb(void)
 
        { &hf_smb_timeout,
                { "Timeout", "smb.timeout", FT_UINT32, BASE_DEC,
-               NULL, 0, "Timeout in miliseconds", HFILL }},
+               NULL, 0, "Timeout in milliseconds", HFILL }},
 
        { &hf_smb_high_offset,
                { "High Offset", "smb.offset_high", FT_UINT32, BASE_DEC,
@@ -17759,7 +18320,7 @@ proto_register_smb(void)
 
        { &hf_smb_resume_key_len,
                { "Resume Key Length", "smb.resume.key_len", FT_UINT16, BASE_DEC,
-               NULL, 0, "Resume Key length", HFILL }},
+               NULL, 0, NULL, HFILL }},
 
        { &hf_smb_resume_find_id,
                { "Find ID", "smb.resume.find_id", FT_UINT8, BASE_HEX,
@@ -17909,6 +18470,14 @@ proto_register_smb(void)
                { "Disconnect TID", "smb.connect.flags.dtid", FT_BOOLEAN, 16,
                TFS(&tfs_disconnect_tid), 0x0001, "Disconnect TID?", HFILL }},
 
+       { &hf_smb_connect_flags_ext_sig,
+               { "Extended Signature", "smb.connect.flags.extendedsig", FT_BOOLEAN, 16,
+               TFS(&tfs_extended_signature), 0x0004, "Extended signature?", HFILL }},
+
+       { &hf_smb_connect_flags_ext_resp,
+               { "Extended Response", "smb.connect.flags.extendedresp", FT_BOOLEAN, 16,
+               TFS(&tfs_extended_response), 0x0008, "Extended response?", HFILL }},
+
        { &hf_smb_connect_support_search,
                { "Search Bits", "smb.connect.support.search", FT_BOOLEAN, 16,
                TFS(&tfs_connect_support_search), 0x0001, "Exclusive Search Bits supported?", HFILL }},
@@ -17917,6 +18486,18 @@ proto_register_smb(void)
                { "In Dfs", "smb.connect.support.dfs", FT_BOOLEAN, 16,
                TFS(&tfs_connect_support_in_dfs), 0x0002, "Is this in a Dfs tree?", HFILL }},
 
+       { &hf_smb_connect_support_csc_mask_vals,
+               { "CSC Mask", "smb.connect.support.cscmask", FT_UINT16, BASE_DEC,
+               VALS(connect_support_csc_mask_vals), 0x000c, "CSC mask?", HFILL }},
+
+       { &hf_smb_connect_support_uniquefilename,
+               { "Unique File Name", "smb.connect.support.uniqfilename", FT_BOOLEAN, 16,
+               TFS(&tfs_connect_support_uniquefilename), 0x0010, "Unique file name supported?", HFILL }},
+
+       { &hf_smb_connect_support_extended_signature,
+               { "Extended Signatures", "smb.connect.support.extendedsig", FT_BOOLEAN, 16,
+               TFS(&tfs_connect_support_extended_signature), 0x0020, "Extended signatures?", HFILL }},
+
        { &hf_smb_max_setup_count,
                { "Max Setup Count", "smb.msc", FT_UINT8, BASE_DEC,
                NULL, 0, "Maximum number of setup words to return", HFILL }},
@@ -18228,7 +18809,7 @@ proto_register_smb(void)
 
        { &hf_smb_nt_create_options_sequential_only,
                { "Sequential Only", "smb.nt.create_options.sequential_only", FT_BOOLEAN, 32,
-               TFS(&tfs_nt_create_options_sequential_only), 0x00000004, "Will access to thsis file only be sequential?", HFILL }},
+               TFS(&tfs_nt_create_options_sequential_only), 0x00000004, "Will access to this file only be sequential?", HFILL }},
 
        { &hf_smb_nt_create_options_no_intermediate_buffering,
                { "Intermediate Buffering", "smb.nt.create_options.intermediate_buffering", FT_BOOLEAN, 32,
@@ -18375,19 +18956,19 @@ proto_register_smb(void)
 
        { &hf_smb_nt_qsd_owner,
                { "Owner", "smb.nt_qsd.owner", FT_BOOLEAN, 32,
-               TFS(&tfs_nt_qsd_owner), NT_QSD_OWNER, "Is owner security informaton being queried?", HFILL }},
+               TFS(&tfs_nt_qsd_owner), NT_QSD_OWNER, "Is owner security information being queried?", HFILL }},
 
        { &hf_smb_nt_qsd_group,
                { "Group", "smb.nt_qsd.group", FT_BOOLEAN, 32,
-               TFS(&tfs_nt_qsd_group), NT_QSD_GROUP, "Is group security informaton being queried?", HFILL }},
+               TFS(&tfs_nt_qsd_group), NT_QSD_GROUP, "Is group security information being queried?", HFILL }},
 
        { &hf_smb_nt_qsd_dacl,
                { "DACL", "smb.nt_qsd.dacl", FT_BOOLEAN, 32,
-               TFS(&tfs_nt_qsd_dacl), NT_QSD_DACL, "Is DACL security informaton being queried?", HFILL }},
+               TFS(&tfs_nt_qsd_dacl), NT_QSD_DACL, "Is DACL security information being queried?", HFILL }},
 
        { &hf_smb_nt_qsd_sacl,
                { "SACL", "smb.nt_qsd.sacl", FT_BOOLEAN, 32,
-               TFS(&tfs_nt_qsd_sacl), NT_QSD_SACL, "Is SACL security informaton being queried?", HFILL }},
+               TFS(&tfs_nt_qsd_sacl), NT_QSD_SACL, "Is SACL security information being queried?", HFILL }},
 
        { &hf_smb_extended_attributes,
                { "Extended Attributes", "smb.ext_attr", FT_BYTES, BASE_NONE,
@@ -18419,7 +19000,7 @@ proto_register_smb(void)
 
        { &hf_smb_root_dir_handle,
                { "Root Directory Handle", "smb.root_dir_handle", FT_UINT32, BASE_HEX,
-               NULL, 0, "Root directory handle", HFILL }},
+               NULL, 0, NULL, HFILL }},
 
        { &hf_smb_target_name_len,
                { "Target name length", "smb.target_name_len", FT_UINT32, BASE_DEC,
@@ -18442,7 +19023,7 @@ proto_register_smb(void)
                NULL, 0, "Offset to next entry", HFILL }},
 
        { &hf_smb_change_time,
-               { "Change", "smb.change.time", FT_ABSOLUTE_TIME, BASE_NONE,
+               { "Change", "smb.change.time", FT_ABSOLUTE_TIME, ABSOLUTE_TIME_LOCAL,
                NULL, 0, "Last Change Time", HFILL }},
 
        { &hf_smb_setup_len,
@@ -18462,7 +19043,7 @@ proto_register_smb(void)
                NULL, 0, "Index of entry after last returned", HFILL }},
 
        { &hf_smb_print_queue_date,
-               { "Queued", "smb.print.queued.date", FT_ABSOLUTE_TIME, BASE_NONE,
+               { "Queued", "smb.print.queued.date", FT_ABSOLUTE_TIME, ABSOLUTE_TIME_LOCAL,
                NULL, 0, "Date when this entry was queued", HFILL }},
 
        { &hf_smb_print_queue_dos_date,
@@ -18745,7 +19326,7 @@ proto_register_smb(void)
 
        { &hf_smb_dfs_referral_number_of_expnames,
                { "Number of Expanded Names", "smb.dfs.referral.number_of_expnames", FT_UINT16, BASE_DEC,
-               NULL, 0, "Number of expanded names", HFILL }},
+               NULL, 0, NULL, HFILL }},
 
        { &hf_smb_dfs_referral_expnames_offset,
                { "Expanded Names Offset", "smb.dfs.referral.expnames_offset", FT_UINT16, BASE_DEC,
@@ -18785,7 +19366,7 @@ proto_register_smb(void)
 
        { &hf_smb_file_index,
                { "File Index", "smb.file_index", FT_UINT32, BASE_DEC,
-               NULL, 0, "File index", HFILL }},
+               NULL, 0, NULL, HFILL }},
 
        { &hf_smb_short_file_name,
                { "Short File Name", "smb.short_file", FT_STRING, BASE_NONE,
@@ -18809,7 +19390,7 @@ proto_register_smb(void)
 
        { &hf_smb_fs_sector,
                { "Bytes per Sector", "smb.fs_bytes_per_sector", FT_UINT32, BASE_DEC,
-               NULL, 0, "Bytes per sector", HFILL }},
+               NULL, 0, NULL, HFILL }},
 
        { &hf_smb_avail_units,
                { "Available Units", "smb.avail.units", FT_UINT32, BASE_DEC,
@@ -18817,7 +19398,7 @@ proto_register_smb(void)
 
        { &hf_smb_volume_serial_num,
                { "Volume Serial Number", "smb.volume.serial", FT_UINT32, BASE_HEX,
-               NULL, 0, "Volume serial number", HFILL }},
+               NULL, 0, NULL, HFILL }},
 
        { &hf_smb_volume_label_len,
                { "Label Length", "smb.volume.label.len", FT_UINT32, BASE_DEC,
@@ -18840,8 +19421,8 @@ proto_register_smb(void)
                NULL, 0, "Number of actual free allocation units", HFILL }},
 
        { &hf_smb_soft_quota_limit,
-               { "(Soft) Quota Treshold", "smb.quota.soft.default", FT_UINT64, BASE_DEC,
-               NULL, 0, "Soft Quota treshold", HFILL }},
+               { "(Soft) Quota Threshold", "smb.quota.soft.default", FT_UINT64, BASE_DEC,
+               NULL, 0, "Soft Quota threshold", HFILL }},
 
        { &hf_smb_hard_quota_limit,
                { "(Hard) Quota Limit", "smb.quota.hard.default", FT_UINT64, BASE_DEC,
@@ -18995,6 +19576,10 @@ proto_register_smb(void)
                { "Defragmentation error", "smb.segment.error", FT_FRAMENUM, BASE_NONE, NULL, 0x0,
                        "Defragmentation error due to illegal fragments", HFILL }},
 
+       { &hf_smb_reassembled_length,
+               { "Reassembled SMB length", "smb.reassembled.length", FT_UINT32, BASE_DEC, NULL, 0x0,
+                       "The total length of the reassembled payload", HFILL }},
+
        { &hf_smb_opened_in,
                { "Opened in", "smb.fid.opened_in", FT_FRAMENUM, BASE_NONE, NULL, 0x0,
                        "The frame this fid was opened", HFILL }},
@@ -19112,15 +19697,15 @@ proto_register_smb(void)
            NULL, 0, "Number of bytes used to store the file", HFILL }},
 
        { &hf_smb_unix_file_last_status,
-         { "Last status change", "smb.unix.file.stime", FT_ABSOLUTE_TIME, BASE_NONE,
+         { "Last status change", "smb.unix.file.stime", FT_ABSOLUTE_TIME, ABSOLUTE_TIME_LOCAL,
            NULL, 0, NULL, HFILL }},
 
        { &hf_smb_unix_file_last_access,
-         { "Last access", "smb.unix.file.atime", FT_ABSOLUTE_TIME, BASE_NONE,
+         { "Last access", "smb.unix.file.atime", FT_ABSOLUTE_TIME, ABSOLUTE_TIME_LOCAL,
            NULL, 0, NULL, HFILL }},
 
        { &hf_smb_unix_file_last_change,
-         { "Last modification", "smb.unix.file.mtime", FT_ABSOLUTE_TIME, BASE_NONE,
+         { "Last modification", "smb.unix.file.mtime", FT_ABSOLUTE_TIME, ABSOLUTE_TIME_LOCAL,
            NULL, 0, NULL, HFILL }},
 
        { &hf_smb_unix_file_uid,
@@ -19168,7 +19753,7 @@ proto_register_smb(void)
            NULL, 0, NULL, HFILL }},
 
         { &hf_smb_network_unknown,
-          { "Unknown field", "smb.unknown", FT_UINT32, BASE_HEX,
+          { "Unknown field", "smb.unknown_field", FT_UINT32, BASE_HEX,
             NULL, 0, NULL, HFILL }},
 
         { &hf_smb_create_flags,
@@ -19216,7 +19801,7 @@ proto_register_smb(void)
                NULL, 0, NULL, HFILL }},
 
        { &hf_smb_file_rw_offset,
-         { "File Offset", "smb.file.rw.offset", FT_UINT32, BASE_DEC,
+         { "File Offset", "smb.file.rw.offset", FT_UINT64, BASE_DEC,
                NULL, 0, NULL, HFILL }},
 
        { &hf_smb_file_rw_length,
@@ -19237,7 +19822,7 @@ proto_register_smb(void)
 
        { &hf_smb_posix_ace_type,
          { "ACE Type", "smb.posix_acl.ace_type", FT_UINT8, BASE_DEC,
-               VALS(&ace_type_vals), 0, NULL, HFILL }},
+               VALS(ace_type_vals), 0, NULL, HFILL }},
 
        { &hf_smb_posix_ace_flags,
          { "Permissions", "smb.posix_acl.ace_perms", FT_UINT8, BASE_HEX,
@@ -19377,9 +19962,18 @@ proto_register_smb(void)
                "Whether the dissector should snoop SMB and related CIFS protocols to discover and display Names associated with SIDs",
                &sid_name_snooping);
 
+       /* For display of SIDs and RIDs in Hex option */
+       prefs_register_bool_preference(smb_module, "sid_display_hex",
+               "Display SIDs in Hex",
+               "Whether the dissector should display SIDs and RIDs in hexadecimal rather than decimal",
+               &sid_display_hex);
+
        register_init_routine(smb_trans_reassembly_init);
        smb_tap = register_tap("smb");
 
+        /* Register the tap for the "Export Object" function */
+        smb_eo_tap = register_tap("smb_eo"); /* SMB Export Object tap */
+
        register_dissector("smb", dissect_smb, proto_smb);
 }