This sort of looks like a cross post, or an off-topic message from the
subject, but it's not:
Can someone with a *nix SPF implmentation and DNS server please try a
simple test for me.
Create a DNS TXT record like:
Windnsbug TXT ( ""
"v=spf1 "
""
""
"+mx "
""
"-all"
""
"" )
And then use your spftest program to read it. I'd expect the record to
look like "v=spf1 +mx -all" when you get to your parser as I expect
many other people would, however on Windows, I can't even process the
TXT record under some circumstances because the Windows 2K Dns API
DnsQuery barfs when in ANSI mode and corrupts my heap when in UNICODE
mode - bletch!
I've opened a case with Microsoft on this because it looks like a
vulnerability that could cause an least a DOS attack on a system that
tries to read the DNS TXT record and at worst a way to deliver a
virus/worm to a Windows system simply by sending you an email - hideous
I think you'll agree.
If you don't have Windows, then stop reading now, otherwise, this is the
case file that I forwarded to MS...
========================================================================
========
Bug in DnsQuery
===============
Symptoms
========
DnsQuery cannot read DNS TXT records with empty strings and will either
crash the process (DnsQuery_A) or return an invalid data set
(DnsQuery_W) which subsequently corrupts the callers heap.
Steps to reproduce
==================
On a DNS server, create a TXT record with the following shape.
windnsbug TXT ( ""
"abc"
""
"def"
""
"this is"
""
"gonna break"
""
"" )
Either enter this via the DNS UI, or create a TXT record named
"windnsbug" and then edit the
%WindowsSystem32%\dns\windnsbug.<domain>.dns file and replace the TXT
record with the above.
Next on a Windows 2000/Windows XP system with Visual Studio installed,
start a console project and replace the main code with:
------------------------------------------------------------------------
--
// DNSBug.cpp : Defines the entry point for the console application. //
#include "stdafx.h"
#include <windows.h>
#include <windns.h>
#pragma comment(lib, "Dnsapi.lib" )
int _tmain(int argc, _TCHAR* argv[])
{
// First go, this is OK until the DnsRecordListFree
try
{
PDNS_RECORD pRecs;
// Replace the domain below with your domain (or leave
it as is and use ours)
DNS_STATUS stat = DnsQuery_W( L"dnsbug.exclaimer.co.uk",
DNS_TYPE_TEXT, DNS_QUERY_STANDARD | DNS_QUERY_BYPASS_CACHE, NULL,
&pRecs, NULL );
if ( stat == 0 )
{
for(DWORD
dw=0;dw<pRecs->Data.TXT.dwStringCount;dw++)
printf( "DnsQuery_W: Text string %d is
%S\r\n", dw, pRecs->Data.TXT.pStringArray[dw] );
DnsRecordListFree( pRecs, DnsFreeRecordListDeep
);
}
}
catch( ... )
{
printf("DnsQuery_W faulted\r\n");
}
// Second go, this is gonna crash ...
try
{
PDNS_RECORD pRecs;
// Replace the domain below with your domain (or leave
it as is and use ours)
DNS_STATUS stat = DnsQuery_A( "dnsbug.exclaimer.co.uk",
DNS_TYPE_TEXT, DNS_QUERY_STANDARD | DNS_QUERY_BYPASS_CACHE, NULL,
&pRecs, NULL );
if ( stat == 0 )
{
for(DWORD
dw=0;dw<pRecs->Data.TXT.dwStringCount;dw++)
printf( "DnsQuery_A: Text string %d is
%s\r\n", dw, pRecs->Data.TXT.pStringArray[dw] );
DnsRecordListFree( pRecs, DnsFreeRecordListDeep
);
}
}
catch( ... )
{
printf("DnsQuery_A faulted\r\n");
}
printf("End\r\n");
return 0;
}
------------------------------------------------------
Compile and run the program. Notice that the output from the DnsQuery_W
part has strange characters at the start of each line.
Concerns
========
With the the coming of Microsoft CallerID and SPF (various tools in the
fight against spam), DNS servers are starting to publish more
information in TXT records.
Many MTAs on Windows will be reading this data (including our product
Exclaimer (www.exclaimer.net)) using the DnsQuery API.
These processes may encounter DNS TXT records setup by a malicious user
in such as fashion as to cause code of their own liking to be executed
on the target system just by simply delivering a piece of email to that
server.
========================================================================
==========================
Further research
================
As I understand it, the strings are supposed to have a length octet
leading them in followed by the string which is not null terminated. In
the example above I'd expect the data in the RR to be 33 bytes long in
this shape:
0 1 2 3 4 5 6 7
+---+---+---+---+---+---+---+---+
| 0 | 3 |'a'|'b'|'c'|'0'|'3'|'d'|
+---+---+---+---+---+---+---+---+
8 9 10 11 12 13 14 15
+---+---+---+---+---+---+---+---+
|'e'|'f'| 0 | 7 |'t'|'h'|'i'|'s'|
+---+---+---+---+---+---+---+---+
16 17 18 19 20 21 22 23
+---+---+---+---+---+---+---+---+
|' '|'i'|'s'| 0 | a |'g'|'o'|'n'|
+---+---+---+---+---+---+---+---+
24 25 26 27 28 29 30 31
+---+---+---+---+---+---+---+---+
|'n'|'a'|' '|'b'|'r'|'e'|'a'|'k'|
+---+---+---+---+---+---+---+---+
32 33
+---+---+
| 0 | 0 |
+---+---+
Spookily, in the case where the API DnsQuery_W which doesn't crash
internally (but corrupts the heap during free), the strings returned
from the Windows API are:
p[0] = "\3abc"
p[1] = "abc"
p[2] = "\3"
p[3] = "def "
p[4] = "\7this is"
p[5] = "this is"
p[6] = "\agonna break"
p[7] = "gonna break"
p[8] = ""
p[9] = ""
NSLOOKUP in debug & d2 mode returns the fact that there were 33 bytes of
data, lending weight to the fact that the record is not invalid in the
DNS server, and it only printing out 4 strings (which is sort of
expected).
Thanks,
Gary
This message (and any associated files) is intended only for the use of spf-devel@v2.listbox.com and may contain information that is confidential, subject to copyright or constitutes a trade secret. If you are not spf-devel@v2.listbox.com you are hereby notified that any dissemination, copying or distribution of this message, or files associated with this message, is strictly prohibited. If you have received this message in error, please notify us immediately by replying to the message and deleting it from your computer. Messages sent to and from us may be monitored. Any views or opinions presented are solely those of the author gary@exclaimer.net and do not necessarily represent those of the company.
This disclaimer was added by eXclaimer for Microsoft Exchange 2000, a DCSL product. Please visit our web site at www.exclaimer.co.uk for more information.
-------
To unsubscribe, change your address, or temporarily deactivate your subscription,
please go to http://v2.listbox.com/member/?listname=spf-devel@v2.listbox.com
subject, but it's not:
Can someone with a *nix SPF implmentation and DNS server please try a
simple test for me.
Create a DNS TXT record like:
Windnsbug TXT ( ""
"v=spf1 "
""
""
"+mx "
""
"-all"
""
"" )
And then use your spftest program to read it. I'd expect the record to
look like "v=spf1 +mx -all" when you get to your parser as I expect
many other people would, however on Windows, I can't even process the
TXT record under some circumstances because the Windows 2K Dns API
DnsQuery barfs when in ANSI mode and corrupts my heap when in UNICODE
mode - bletch!
I've opened a case with Microsoft on this because it looks like a
vulnerability that could cause an least a DOS attack on a system that
tries to read the DNS TXT record and at worst a way to deliver a
virus/worm to a Windows system simply by sending you an email - hideous
I think you'll agree.
If you don't have Windows, then stop reading now, otherwise, this is the
case file that I forwarded to MS...
========================================================================
========
Bug in DnsQuery
===============
Symptoms
========
DnsQuery cannot read DNS TXT records with empty strings and will either
crash the process (DnsQuery_A) or return an invalid data set
(DnsQuery_W) which subsequently corrupts the callers heap.
Steps to reproduce
==================
On a DNS server, create a TXT record with the following shape.
windnsbug TXT ( ""
"abc"
""
"def"
""
"this is"
""
"gonna break"
""
"" )
Either enter this via the DNS UI, or create a TXT record named
"windnsbug" and then edit the
%WindowsSystem32%\dns\windnsbug.<domain>.dns file and replace the TXT
record with the above.
Next on a Windows 2000/Windows XP system with Visual Studio installed,
start a console project and replace the main code with:
------------------------------------------------------------------------
--
// DNSBug.cpp : Defines the entry point for the console application. //
#include "stdafx.h"
#include <windows.h>
#include <windns.h>
#pragma comment(lib, "Dnsapi.lib" )
int _tmain(int argc, _TCHAR* argv[])
{
// First go, this is OK until the DnsRecordListFree
try
{
PDNS_RECORD pRecs;
// Replace the domain below with your domain (or leave
it as is and use ours)
DNS_STATUS stat = DnsQuery_W( L"dnsbug.exclaimer.co.uk",
DNS_TYPE_TEXT, DNS_QUERY_STANDARD | DNS_QUERY_BYPASS_CACHE, NULL,
&pRecs, NULL );
if ( stat == 0 )
{
for(DWORD
dw=0;dw<pRecs->Data.TXT.dwStringCount;dw++)
printf( "DnsQuery_W: Text string %d is
%S\r\n", dw, pRecs->Data.TXT.pStringArray[dw] );
DnsRecordListFree( pRecs, DnsFreeRecordListDeep
);
}
}
catch( ... )
{
printf("DnsQuery_W faulted\r\n");
}
// Second go, this is gonna crash ...
try
{
PDNS_RECORD pRecs;
// Replace the domain below with your domain (or leave
it as is and use ours)
DNS_STATUS stat = DnsQuery_A( "dnsbug.exclaimer.co.uk",
DNS_TYPE_TEXT, DNS_QUERY_STANDARD | DNS_QUERY_BYPASS_CACHE, NULL,
&pRecs, NULL );
if ( stat == 0 )
{
for(DWORD
dw=0;dw<pRecs->Data.TXT.dwStringCount;dw++)
printf( "DnsQuery_A: Text string %d is
%s\r\n", dw, pRecs->Data.TXT.pStringArray[dw] );
DnsRecordListFree( pRecs, DnsFreeRecordListDeep
);
}
}
catch( ... )
{
printf("DnsQuery_A faulted\r\n");
}
printf("End\r\n");
return 0;
}
------------------------------------------------------
Compile and run the program. Notice that the output from the DnsQuery_W
part has strange characters at the start of each line.
Concerns
========
With the the coming of Microsoft CallerID and SPF (various tools in the
fight against spam), DNS servers are starting to publish more
information in TXT records.
Many MTAs on Windows will be reading this data (including our product
Exclaimer (www.exclaimer.net)) using the DnsQuery API.
These processes may encounter DNS TXT records setup by a malicious user
in such as fashion as to cause code of their own liking to be executed
on the target system just by simply delivering a piece of email to that
server.
========================================================================
==========================
Further research
================
As I understand it, the strings are supposed to have a length octet
leading them in followed by the string which is not null terminated. In
the example above I'd expect the data in the RR to be 33 bytes long in
this shape:
0 1 2 3 4 5 6 7
+---+---+---+---+---+---+---+---+
| 0 | 3 |'a'|'b'|'c'|'0'|'3'|'d'|
+---+---+---+---+---+---+---+---+
8 9 10 11 12 13 14 15
+---+---+---+---+---+---+---+---+
|'e'|'f'| 0 | 7 |'t'|'h'|'i'|'s'|
+---+---+---+---+---+---+---+---+
16 17 18 19 20 21 22 23
+---+---+---+---+---+---+---+---+
|' '|'i'|'s'| 0 | a |'g'|'o'|'n'|
+---+---+---+---+---+---+---+---+
24 25 26 27 28 29 30 31
+---+---+---+---+---+---+---+---+
|'n'|'a'|' '|'b'|'r'|'e'|'a'|'k'|
+---+---+---+---+---+---+---+---+
32 33
+---+---+
| 0 | 0 |
+---+---+
Spookily, in the case where the API DnsQuery_W which doesn't crash
internally (but corrupts the heap during free), the strings returned
from the Windows API are:
p[0] = "\3abc"
p[1] = "abc"
p[2] = "\3"
p[3] = "def "
p[4] = "\7this is"
p[5] = "this is"
p[6] = "\agonna break"
p[7] = "gonna break"
p[8] = ""
p[9] = ""
NSLOOKUP in debug & d2 mode returns the fact that there were 33 bytes of
data, lending weight to the fact that the record is not invalid in the
DNS server, and it only printing out 4 strings (which is sort of
expected).
Thanks,
Gary
This message (and any associated files) is intended only for the use of spf-devel@v2.listbox.com and may contain information that is confidential, subject to copyright or constitutes a trade secret. If you are not spf-devel@v2.listbox.com you are hereby notified that any dissemination, copying or distribution of this message, or files associated with this message, is strictly prohibited. If you have received this message in error, please notify us immediately by replying to the message and deleting it from your computer. Messages sent to and from us may be monitored. Any views or opinions presented are solely those of the author gary@exclaimer.net and do not necessarily represent those of the company.
This disclaimer was added by eXclaimer for Microsoft Exchange 2000, a DCSL product. Please visit our web site at www.exclaimer.co.uk for more information.
-------
To unsubscribe, change your address, or temporarily deactivate your subscription,
please go to http://v2.listbox.com/member/?listname=spf-devel@v2.listbox.com