1--- a/source/libsmb/asn1.c
2+++ b/source/libsmb/asn1.c
3@@ -261,6 +261,36 @@
4 	return asn1_read(data, v, 1);
5 }
6
7+/* peek to see if a tag is present */
8+/* this was not ported from samba and may not be identical to libsmb mainline */
9+BOOL asn1_peek_tag(ASN1_DATA *data, uint8 tag)
10+{
11+  uint8 curtag;
12+
13+  if (data->has_error)
14+    return False;
15+
16+  // overflow checking
17+  if (data->ofs + 1 < data->ofs || data->ofs + 1 < 1) {
18+    return False;
19+  }
20+
21+  // boundary checking
22+  if (data->ofs + 1 > data->length) {
23+    return False;
24+  }
25+
26+  memcpy( (void*)&curtag, data->data + data->ofs, 1);
27+
28+  // don't move cursor
29+  // don't set error
30+
31+  if( tag != curtag )
32+    return False;
33+
34+  return True;
35+}
36+
37 /* start reading a nested asn1 structure */
38 BOOL asn1_start_tag(ASN1_DATA *data, uint8 tag)
39 {
40--- a/source/libsmb/clispnego.c
41+++ b/source/libsmb/clispnego.c
42@@ -135,9 +135,16 @@
43
44 	asn1_start_tag(&data,ASN1_APPLICATION(0));
45 	asn1_check_OID(&data,OID_SPNEGO);
46+
47+	/* negTokenInit  [0]  NegTokenInit */
48 	asn1_start_tag(&data,ASN1_CONTEXT(0));
49 	asn1_start_tag(&data,ASN1_SEQUENCE(0));
50
51+	/* mechTypes [0] MechTypeList  OPTIONAL */
52+
53+	/* Not really optional, we depend on this to decide
54+	 * what mechanisms we have to work with. */
55+
56 	asn1_start_tag(&data,ASN1_CONTEXT(0));
57 	asn1_start_tag(&data,ASN1_SEQUENCE(0));
58 	for (i=0; asn1_tag_remaining(&data) > 0 && i < ASN1_MAX_OIDS-1; i++) {
59@@ -150,7 +157,39 @@
60 	asn1_end_tag(&data);
61
62 	*principal = NULL;
63-	if (asn1_tag_remaining(&data) > 0) {
64+
65+  /*
66+	   Win7 + Live Sign-in Assistant attaches a mechToken
67+	   ASN1_CONTEXT(2) to the negTokenInit packet
68+	   which breaks our negotiation if we just assume
69+	   the next tag is ASN1_CONTEXT(3).
70+	 */
71+
72+	 if (asn1_peek_tag(&data, ASN1_CONTEXT(1))) {
73+	         uint8 flags;
74+
75+    /* reqFlags [1] ContextFlags  OPTIONAL */
76+    asn1_start_tag(&data, ASN1_CONTEXT(1));
77+    asn1_start_tag(&data, ASN1_BITFIELD);
78+    while (asn1_tag_remaining(&data) > 0) {
79+      asn1_read_uint8(&data, &flags);
80+    }
81+    asn1_end_tag(&data);
82+    asn1_end_tag(&data);
83+  }
84+
85+  if (asn1_peek_tag(&data, ASN1_CONTEXT(2))) {
86+    /* mechToken [2] OCTET STRING  OPTIONAL */
87+    DATA_BLOB token;
88+    asn1_start_tag(&data, ASN1_CONTEXT(2));
89+    asn1_read_OctetString(&data, &token);
90+    asn1_end_tag(&data);
91+    /* Throw away the token - not used. */
92+    data_blob_free(&token);
93+  }
94+
95+  if (asn1_peek_tag(&data, ASN1_CONTEXT(3))) {
96+	     /* mechListMIC [3] OCTET STRING  OPTIONAL */
97 		asn1_start_tag(&data, ASN1_CONTEXT(3));
98 		asn1_start_tag(&data, ASN1_SEQUENCE(0));
99 		asn1_start_tag(&data, ASN1_CONTEXT(0));
100