<?xml version="1.0" encoding="UTF-8" ?>
<?xml-stylesheet type="text/xsl" href="http://blogs.msdn.com/utility/FeedStylesheets/atom.xsl" media="screen"?><feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en-US"><title type="html">The Old New Thing</title><subtitle type="html">not actually &lt;A HREF="http://blogs.msdn.com/oldnewthing/archive/2008/07/17/8741112.aspx#8750046"&gt;to establish a blogging point where individuals can enrich their learns on facilitating and leveraging .NET-related activities most effectively&lt;/A&gt;</subtitle><id>http://blogs.msdn.com/oldnewthing/atom.xml</id><link rel="alternate" type="text/html" href="http://blogs.msdn.com/oldnewthing/default.aspx" /><link rel="self" type="application/atom+xml" href="http://blogs.msdn.com/oldnewthing/atom.xml" /><generator uri="http://communityserver.org" version="2.1.61025.2">Community Server</generator><updated>2009-12-17T07:00:00Z</updated><entry><title>How does the keyboard autorepeat setting work?</title><link rel="alternate" type="text/html" href="http://blogs.msdn.com/oldnewthing/archive/2009/12/28/9941455.aspx" /><id>http://blogs.msdn.com/oldnewthing/archive/2009/12/28/9941455.aspx</id><published>2009-12-28T15:00:00Z</published><updated>2009-12-28T15:00:00Z</updated><content type="html">&lt;P&gt;
Commenter eric johnson wonders
&lt;A HREF="http://blogs.msdn.com/oldnewthing/pages/407234.aspx#735946"&gt;
how that control panel keyboard autorepeat setting works&lt;/A&gt;.
&lt;/P&gt;
&lt;P&gt;
This is one of those questions that has many answers,
depending on how deep you want to dig.
&lt;/P&gt;
&lt;P&gt;
The first layer of the question is how the control panel changes
the keyboard autorepeat rate.
That's simple:
It uses &lt;CODE&gt;SystemParametersInfo(SPI_SETKEYBOARDSPEED)&lt;/CODE&gt;.
From the documentation, you can see that the keyboard speed is an
integer in the range 0..31,
where 0 indicates 2 characters per second
and 31 indicates approximately 30 characters
per second.
&lt;/P&gt;
&lt;P&gt;
The next layer of the question is why the &lt;CODE&gt;SystemParametersInfo&lt;/CODE&gt;
expresses the keyboard autorepeat setting in a 0..31 range,
and why the upper end of the range is 30 characters per second.
Well, the &lt;CODE&gt;SystemParametersInfo&lt;/CODE&gt; function is
merely passing the buck;
that is the format that the Windows keyboard driver uses.
&lt;/P&gt;
&lt;P&gt;
Okay, so why does the Windows keyboard driver use this representation
for the keyboard speed?
Because
&lt;A HREF="http://web.archive.org/web/20080822115611/http://www.computer-engineering.org/ps2keyboard/"&gt;
that's how the hardware keyboard autorepeat setting works&lt;/A&gt;.
Command 0xF3 sets the keyboard autorepeat, and it takes a single
byte argument, of which the bottom five bits encode the autorepeat
speed, ranging from 2 characters per second up to 30.
(That document describes the PS/2 keyboard interface, but the PS/2
command interface was based on the AT interface,
for which the typematic control commands were the same.
The XT keyboard did not have a configurable autorepeat as far as I can tell.
Note that
&lt;A HREF="http://blogs.msdn.com/oldnewthing/archive/2009/09/18/9896621.aspx#9897076"&gt;
typematic was implemented in the hardware, not in the BIOS&lt;/A&gt;.)
&lt;/P&gt;
&lt;P&gt;
So at the end of the day,
it all goes back to the 8042 keyboard controller chip.
The hardware interface was reflected in the driver interface,
which was reflected in the application interface.
And when you issued the application call to change the keyboard
autorepeat speed, that call went to the hardware;
it was the hardware that actually did the autorepeating.
&lt;/P&gt;
&lt;P&gt;
Since the semantics were codified in the application interface,
they were locked into the &lt;CODE&gt;SystemParametersInfo&lt;/CODE&gt;
function even as the driver model and the
keyboard hardware changed around it.
(But I believe that
if you're using a PS/2 keyboard, then the PS/2 keyboard driver
will still defer the actual work of autorepeat to the physical hardware,
so at least the semantics are still applicable.)
&lt;/P&gt;
&lt;img src="http://blogs.msdn.com/aggbug.aspx?PostID=9941455" width="1" height="1"&gt;</content><author><name>oldnewthing</name><uri>http://blogs.msdn.com/members/oldnewthing.aspx</uri></author><category term="History" scheme="http://blogs.msdn.com/oldnewthing/archive/tags/History/default.aspx" /></entry><entry><title>Merry Christmas to me: Zune headphones</title><link rel="alternate" type="text/html" href="http://blogs.msdn.com/oldnewthing/archive/2009/12/25/9941074.aspx" /><id>http://blogs.msdn.com/oldnewthing/archive/2009/12/25/9941074.aspx</id><published>2009-12-25T15:00:01Z</published><updated>2009-12-25T15:00:01Z</updated><content type="html">&lt;P&gt;
My article some time back about
&lt;A HREF="http://blogs.msdn.com/oldnewthing/archive/2009/10/13/9906360.aspx"&gt;
accidentally destroying my beloved Zune headphones&lt;/A&gt;
resulted in a number of people sending me their unwanted Zune headphones
via inter-office mail.
This was not my intention when I posted the article&amp;mdash;if
that were my goal, I would have posted the article immediately
instead of waiting a year and a half!&amp;mdash;but it was nevertheless
a pleasant surprise.
Every so often
&lt;A HREF="https://blogs.msdn.com/oldnewthing/archive/2008/03/17/8080157.aspx"&gt;
strangers come through&lt;/A&gt;.
&lt;/P&gt;
&lt;P&gt;
Thanks, everybody.
&lt;/P&gt;
&lt;img src="http://blogs.msdn.com/aggbug.aspx?PostID=9941074" width="1" height="1"&gt;</content><author><name>oldnewthing</name><uri>http://blogs.msdn.com/members/oldnewthing.aspx</uri></author><category term="Non-Computer" scheme="http://blogs.msdn.com/oldnewthing/archive/tags/Non-Computer/default.aspx" /></entry><entry><title>No, you didn't win the Jethro Tull box set, and please tell everybody else in your area code to stop calling me</title><link rel="alternate" type="text/html" href="http://blogs.msdn.com/oldnewthing/archive/2009/12/25/9941073.aspx" /><id>http://blogs.msdn.com/oldnewthing/archive/2009/12/25/9941073.aspx</id><published>2009-12-25T15:00:00Z</published><updated>2009-12-25T15:00:00Z</updated><content type="html">&lt;P&gt;
Some time ago, a fellow employee started
receiving mysterious fax calls at the office four or five times a day
and had to call the Microsoft telephone services folks to block
the caller.
But this reminded another colleague of a much more annoying problem,
and one for which caller-block would not have worked.
&lt;/P&gt;
&lt;BLOCKQUOTE CLASS=q&gt;
&lt;P&gt;
A local radio station had a contest line in
the 206 area code.
If someone in the 425 area code
dialed this number
without dialing the 206 area code prefix,
they rang the phone of a new Microsoft employee.
That employee's phone was set up incorrectly,
and the calls ended up auto-forwarded to my phone.
Every time the radio station ran a contest,
my phone lit up like a Christmas tree.
&lt;/P&gt;
&lt;P&gt;
The telephone services department had to retire the phone number
that matched the radio station's number.
&lt;/P&gt;
&lt;P&gt;
It's a pretty funny story, but only in retrospect.
&lt;/P&gt;
&lt;/BLOCKQUOTE&gt;
&lt;P&gt;
Background information (simplified) for those unfamiliar
with United States telephone dialing rules:
To make a call within an area code, you just dial the last
seven digits.
To make calls between area codes, you dial all ten digits.
The contest number was (206)&amp;nbsp;555-1212, and people in
the 425 area code who forgot to dial the 206 prefix ended
up calling (425)&amp;nbsp;555-1212 by mistake.
(In parts of the country with &lt;I&gt;ten-digit dialing&lt;/I&gt;,
the area code is mandatory even for calls originating from the same area code.)
&lt;/P&gt;
&lt;P&gt;
&lt;B&gt;Forgot to knock on wood&lt;/B&gt;:
Barely a week after my colleague told the story
of the radio station contest line,
it happened again.
The telephone department once again
assigned the troublesome number to a new Microsoft employee,
and due to the incorrect set-up, my colleague's phone once again
started ringing whenever the local radio station announced
a call-in contest.
&lt;/P&gt;
&lt;P&gt;
This time, the telephone support people placed a permanent block
on the troublesome phone number, so it will never be used for
anything again.
Well, more accurately, they tried three times, and the third time
it finally worked (knock on wood).
And nobody every figured out why the number forwarded to my
colleague's phone.
Some things will always be a mystery...
&lt;/P&gt;
&lt;img src="http://blogs.msdn.com/aggbug.aspx?PostID=9941073" width="1" height="1"&gt;</content><author><name>oldnewthing</name><uri>http://blogs.msdn.com/members/oldnewthing.aspx</uri></author><category term="Non-Computer" scheme="http://blogs.msdn.com/oldnewthing/archive/tags/Non-Computer/default.aspx" /></entry><entry><title>The NPR Planet Money one-hour story competition: The shopping mall convention</title><link rel="alternate" type="text/html" href="http://blogs.msdn.com/oldnewthing/archive/2009/12/24/9940798.aspx" /><id>http://blogs.msdn.com/oldnewthing/archive/2009/12/24/9940798.aspx</id><published>2009-12-24T15:00:01Z</published><updated>2009-12-24T15:00:01Z</updated><content type="html">&lt;P&gt;
Voting closed last night on the second
NPR Planet Money one-hour story competition.
Three reporters were sent into a convention
(this time, the
&lt;I&gt;International Council of Shopping Centers&lt;/i&gt; conference)
and given one hour to collect tape for a story.
&lt;A HREF="http://www.npr.org/blogs/money/2009/12/podcast_iron_reporter_competit.html"&gt;
Listen to the results&lt;/A&gt;,
either in the full podcast format or just to the three individual stories.
&lt;/P&gt;
&lt;P&gt;
Each of the stories was interesting in its own way.
From Adam Davidson, I learned some mall restaurant jargon.
From Chana Joffe-Walt, I learned about the pursuit of the cool kids.
And from Alex Blumberg, I learned why a guy
dressed in a bright red blazer
known only as &lt;I&gt;McGuire&lt;/I&gt;
is the most popular guy at the convention.
&lt;/P&gt;
&lt;P&gt;
My vote went to Chana's story.
&lt;/P&gt;
&lt;P&gt;
Bonus link:
&lt;A HREF="http://massburger.blogspot.com/"&gt;The Six Guys' Blog&lt;/A&gt;,
the blog of Five Guys.
(This will make sense after you listen to Alex's story.)
&lt;/P&gt;
&lt;img src="http://blogs.msdn.com/aggbug.aspx?PostID=9940798" width="1" height="1"&gt;</content><author><name>oldnewthing</name><uri>http://blogs.msdn.com/members/oldnewthing.aspx</uri></author><category term="Non-Computer" scheme="http://blogs.msdn.com/oldnewthing/archive/tags/Non-Computer/default.aspx" /></entry><entry><title>Why don't we create a special class of programs which can break the normal rules?</title><link rel="alternate" type="text/html" href="http://blogs.msdn.com/oldnewthing/archive/2009/12/24/9940797.aspx" /><id>http://blogs.msdn.com/oldnewthing/archive/2009/12/24/9940797.aspx</id><published>2009-12-24T15:00:00Z</published><updated>2009-12-24T15:00:00Z</updated><content type="html">&lt;P&gt;
In response to a discussion of why the window handle limit is 10,000,
commenter Juan wondered
&lt;A HREF="http://blogs.msdn.com/oldnewthing/archive/2007/07/18/3926581.aspx#3938322"&gt;
why we don't create a special class of programs which can
exceed the 10,000 handle limit&lt;/A&gt; and otherwise bypass
the normal operation of the system.
&lt;/P&gt;
&lt;P&gt;
This is another case of the tragedy of special treatment:
&lt;A HREF="http://blogs.msdn.com/oldnewthing/archive/2008/10/06/8969399.aspx"&gt;
Eventually, nothing is special any more&lt;/A&gt;.
&lt;/P&gt;
&lt;P&gt;
If there were a way for an application to say,
"Hey, I don't want to be constrained by the normal rules
that apply to your everyday boring applications,"
then every application &lt;I&gt;would simply say it&lt;/I&gt;,
and the net effect would be that the constraint
no longer applies to anybody.
&lt;/P&gt;
&lt;P&gt;
Task Manager conforms to the normal rules for GUI programs
because
&lt;A HREF="http://blogs.msdn.com/oldnewthing/archive/2008/09/22/8960761.aspx#8962451"&gt;
if it marked itself as special&lt;/A&gt;,
soon everybody would mark themselves as special in order
to get the same special treatment.
(Besides, the special treatment doesn't help Task Manager at all,
since Task Manager doesn't create 10,000 handles.
The specific issue in the comment is not something Task Manager
even knows that it needs to opt out of.
All it did was call &lt;CODE&gt;CreateWindow&lt;/CODE&gt;;
Task Manager shouldn't need to know about the internal implementation of
&lt;CODE&gt;CreateWindow&lt;/CODE&gt;.)
&lt;/P&gt;
&lt;B&gt;Bonus chatter&lt;/B&gt;:
There is already
&lt;A HREF="http://msdn.microsoft.com/en-us/library/bb625963.aspx"&gt;
one mechanism for applications to say that
a particular class of restrictions should not apply to them&lt;/A&gt;.
&lt;/P&gt;
&lt;img src="http://blogs.msdn.com/aggbug.aspx?PostID=9940797" width="1" height="1"&gt;</content><author><name>oldnewthing</name><uri>http://blogs.msdn.com/members/oldnewthing.aspx</uri></author><category term="Code" scheme="http://blogs.msdn.com/oldnewthing/archive/tags/Code/default.aspx" /></entry><entry><title>Exploiting the inattentive: The posted wine rating may not match the wine on the shelf</title><link rel="alternate" type="text/html" href="http://blogs.msdn.com/oldnewthing/archive/2009/12/23/9940331.aspx" /><id>http://blogs.msdn.com/oldnewthing/archive/2009/12/23/9940331.aspx</id><published>2009-12-23T15:00:01Z</published><updated>2009-12-23T15:00:01Z</updated><content type="html">&lt;P&gt;
The &lt;I&gt;Washington Post&lt;/I&gt;
did a spot check of area wine stores and found that
of the "shelf talkers" signs (those things
that describe the wine and tell you what score it received
from &lt;I&gt;Wine Spectator&lt;/I&gt; magazine) it found,
&lt;A HREF="http://www.washingtonpost.com/wp-dyn/content/article/2007/12/22/AR2007122200399.html"&gt;
a quarter of them were incorrect&lt;/a&gt;,
usually by attributing a good score to the correct wine vineyard but
from a different year.
So when you cruise the wine store, make sure to double-check that
the information placard actually matches the wine it's posted next to.
&lt;/P&gt;
&lt;img src="http://blogs.msdn.com/aggbug.aspx?PostID=9940331" width="1" height="1"&gt;</content><author><name>oldnewthing</name><uri>http://blogs.msdn.com/members/oldnewthing.aspx</uri></author><category term="Non-Computer" scheme="http://blogs.msdn.com/oldnewthing/archive/tags/Non-Computer/default.aspx" /><category term="Exploiting the inattentive" scheme="http://blogs.msdn.com/oldnewthing/archive/tags/Exploiting+the+inattentive/default.aspx" /></entry><entry><title>Why is it possible to destroy a critical section while it is in use?</title><link rel="alternate" type="text/html" href="http://blogs.msdn.com/oldnewthing/archive/2009/12/23/9940330.aspx" /><id>http://blogs.msdn.com/oldnewthing/archive/2009/12/23/9940330.aspx</id><published>2009-12-23T15:00:00Z</published><updated>2009-12-23T15:00:00Z</updated><content type="html">&lt;P&gt;
Some time back,
Stu wondered
&lt;A HREF="http://blogs.msdn.com/oldnewthing/archive/2006/12/11/1259599.aspx#1263540"&gt;
why it is possible to destroy a critical section while it is in use&lt;/A&gt;.
&lt;/P&gt;
&lt;P&gt;
Well, there's nothing stopping you from creating a file that contains
these lines:
&lt;/P&gt;
&lt;PRE&gt;
#include &amp;lt;windows.h&amp;gt;
int __cdecl main(int, char**)
{
  CRITICAL_SECTION cs;
  InitializeCriticalSection(&amp;amp;cs);
  EnterCriticalSection(&amp;amp;cs);
  DeleteCriticalSection(&amp;amp;cs);
  return 0;
}
&lt;/PRE&gt;
&lt;P&gt;
and then telling your compiler to turn it into a program.
It's not like a bolt of lightning is going to come out of the sky
and zap you before you hit the Enter key.
&lt;/P&gt;
&lt;P&gt;
So obviously, it's possible.
&lt;/P&gt;
&lt;P&gt;
On the other hand, it's a bug,
just like closing a handle to a file that another thread is
reading from,
or like closing an event handle that another thread is waiting on.
&lt;/P&gt;
&lt;P&gt;
Critical sections are one of those low-level &lt;I&gt;I sure hope you know what
you're doing because I'm not going to help you if you mess up&lt;/I&gt;
pieces of functionality.
If you use them incorrectly, then you will suffer the consequences,
the same as if you tried to free memory twice
or write to memory after freeing it
or cast a &lt;CODE&gt;Gdiplus::Color*&lt;/CODE&gt; to a &lt;CODE&gt;CComBSTR*&lt;/CODE&gt;.
&lt;/P&gt;
&lt;P&gt;
Are there any legitimate cases where you would delete a critical
section while it is owned?
I sure can't think of any.
&lt;/P&gt;
&lt;P&gt;
If there were a legitimate case for deleting a critical section
while it is owned, what could it be?
Well, it can't be owned by the thread doing the deleting,
because that would imply that you took it in order to prevent
somebody else from entering it (while you deleted it),
but that just creates another race condition:
If you tinker the timing, then you can create this
scenario:
That other thread gets
pre-empted just as it was about to execute the first
instruction of the &lt;CODE&gt;EnterCriticalSection&lt;/CODE&gt; function.
Meanwhile, the destroying thread enters the critical section,
does whatever other stuff it wants to do,
and then deletes the critical section.
That other thread finally gets a chance to run and is now
attempting to enter a deleted critical section, which is clearly
not legal.
&lt;/P&gt;
&lt;P&gt;
Okay, so if there were a legitimate case, it would have to be
deleting a critical section owned by some other thread.
Maybe that other thread enters the critical section, and then
signals the main thread to delete the critical section.
Why would it do that? Who knows.
Maybe it wants to make sure only one thread signals
the main thread.
But you still have the same problem as with the previous case:
You entered the critical section because you wanted to prevent
a third thread from entering the protected region,
but that third thread might have been pre-empted just as it
transferred control to the first instruction of
&lt;CODE&gt;EnterCriticalSection&lt;/CODE&gt;,
and when that third thread finally gets some CPU time,
it proceeds to enter a deleted critical section.
&lt;/P&gt;
&lt;P&gt;
So I can't think of a legitimate reason for deleting a critical
section while it's in use.
Maybe there's a flaw in my logic.
&lt;/P&gt;
&lt;img src="http://blogs.msdn.com/aggbug.aspx?PostID=9940330" width="1" height="1"&gt;</content><author><name>oldnewthing</name><uri>http://blogs.msdn.com/members/oldnewthing.aspx</uri></author><category term="Code" scheme="http://blogs.msdn.com/oldnewthing/archive/tags/Code/default.aspx" /></entry><entry><title>Tweeting Too Hard: Best of Twitter</title><link rel="alternate" type="text/html" href="http://blogs.msdn.com/oldnewthing/archive/2009/12/22/9939869.aspx" /><id>http://blogs.msdn.com/oldnewthing/archive/2009/12/22/9939869.aspx</id><published>2009-12-22T15:00:01Z</published><updated>2009-12-22T15:00:01Z</updated><content type="html">&lt;P&gt;
We had
&lt;A HREF="http://www.craigslist.org/about/best/all/"&gt;
Best of Craig's List&lt;/A&gt;.
&lt;/P&gt;
&lt;P&gt;
We had
&lt;A HREF="http://blogs.msdn.com/oldnewthing/archive/2009/12/11/9935463.aspx"&gt;
Lamebook&lt;/A&gt;.
&lt;/P&gt;
&lt;P&gt;
Now we have
&lt;A HREF="http://tweetingtoohard.com/"&gt;
Tweeting Too Hard&lt;/A&gt;,
"where self-important tweets get the recognition they deserve."
&lt;/P&gt;
&lt;P&gt;
Examples:
&lt;/P&gt;
&lt;BLOCKQUOTE CLASS=m&gt;
The people who say I'm arrogant and shallow
don't see me when I'm at home with my wife.
&lt;A HREF="http://tweetingtoohard.com/t/1949400137"&gt;
Did I mention that she's a former swimsuit model&lt;/A&gt;?
&lt;/BLOCKQUOTE&gt;
&lt;BLOCKQUOTE CLASS=m&gt;
How was it I got
invite to last yrs White House Xmas party when Bush was prez;
and nothing this year?
&lt;A HREF="http://tweetingtoohard.com/t/6738567903"&gt;
I guess I must try harder 2 be fab&lt;/A&gt;.
&lt;/BLOCKQUOTE&gt;
&lt;img src="http://blogs.msdn.com/aggbug.aspx?PostID=9939869" width="1" height="1"&gt;</content><author><name>oldnewthing</name><uri>http://blogs.msdn.com/members/oldnewthing.aspx</uri></author><category term="Non-Computer" scheme="http://blogs.msdn.com/oldnewthing/archive/tags/Non-Computer/default.aspx" /></entry><entry><title>No, you can't lock icons to the user's desktop</title><link rel="alternate" type="text/html" href="http://blogs.msdn.com/oldnewthing/archive/2009/12/22/9939868.aspx" /><id>http://blogs.msdn.com/oldnewthing/archive/2009/12/22/9939868.aspx</id><published>2009-12-22T15:00:00Z</published><updated>2009-12-22T15:00:00Z</updated><content type="html">&lt;P&gt;
In another installment of
&lt;A HREF="http://blogs.msdn.com/oldnewthing/archive/2006/11/01/922449.aspx"&gt;
I bet somebody got a really nice bonus for that feature&lt;/A&gt;,
I submit this question for your consideration.
&lt;/P&gt;
&lt;BLOCKQUOTE CLASS=q&gt;
My customer wants to know how to lock a specific icon to the
upper left hand corner of the desktop.
&lt;/BLOCKQUOTE&gt;
&lt;P&gt;
This company must be writing the most awesome program to end all programs,
a program so amazingly awesome that it should appear as the very first
thing on the desktop so you won't forget how awesome it is.
&lt;/P&gt;
&lt;P&gt;
I think their users may disagree with that assessment.
&lt;/P&gt;
&lt;P&gt;
And the answer is, no, there is no supported way to force a particular
icon to appear at a particular desktop position.
&lt;/P&gt;
&lt;img src="http://blogs.msdn.com/aggbug.aspx?PostID=9939868" width="1" height="1"&gt;</content><author><name>oldnewthing</name><uri>http://blogs.msdn.com/members/oldnewthing.aspx</uri></author><category term="Other" scheme="http://blogs.msdn.com/oldnewthing/archive/tags/Other/default.aspx" /></entry><entry><title>Christmas gift idea for your favorite Microsoft fanboy geek with no sense of fashion or taste</title><link rel="alternate" type="text/html" href="http://blogs.msdn.com/oldnewthing/archive/2009/12/21/9939424.aspx" /><id>http://blogs.msdn.com/oldnewthing/archive/2009/12/21/9939424.aspx</id><published>2009-12-21T15:00:01Z</published><updated>2009-12-21T15:00:01Z</updated><content type="html">&lt;P&gt;
Then again, the "no sense of fashion or taste" may be redundant.
&lt;/P&gt;
&lt;P&gt;
Perhaps you are so enamored of the Microsoft-branded
&lt;A HREF="http://www.sfgate.com/cgi-bin/article.cgi?f=/c/a/2009/03/27/LVTI16LG23.DTL"&gt;
Snuggie&lt;/A&gt;
you received
&lt;A HREF="http://www.flickr.com/photos/94695345@N00/3907945004/"&gt;
at the Company Meeting&lt;/A&gt;
that you can't keep your excitement to yourself
and want to share the joy with a friend.
No problem.
You can now pick one up at the Microsoft Company Store in Redmond,
right across the hall from the
&lt;A HREF="http://www.microsoft.com/about/companyinformation/visitorcenter/default.aspx"&gt;
Visitor Center&lt;/A&gt;.
(The Rapture Index ticks up another notch.)
&lt;/P&gt;
&lt;P&gt;
"You shouldn't have."
&lt;/P&gt;
&lt;P&gt;
&lt;A HREF="http://blogs.msdn.com/oldnewthing/archive/2006/07/31/684106.aspx"&gt;
Previously, in Christmas gift ideas&lt;/A&gt;.
&lt;/P&gt;
&lt;img src="http://blogs.msdn.com/aggbug.aspx?PostID=9939424" width="1" height="1"&gt;</content><author><name>oldnewthing</name><uri>http://blogs.msdn.com/members/oldnewthing.aspx</uri></author><category term="Non-Computer" scheme="http://blogs.msdn.com/oldnewthing/archive/tags/Non-Computer/default.aspx" /></entry><entry><title>What version of the compiler does Raymond use?</title><link rel="alternate" type="text/html" href="http://blogs.msdn.com/oldnewthing/archive/2009/12/21/9939423.aspx" /><id>http://blogs.msdn.com/oldnewthing/archive/2009/12/21/9939423.aspx</id><published>2009-12-21T15:00:00Z</published><updated>2009-12-21T15:00:00Z</updated><content type="html">&lt;P&gt;
From the suggestion box,
&lt;A HREF="http://blogs.msdn.com/oldnewthing/pages/407234.aspx#729260"&gt;
BrianK asks&lt;/A&gt;,
"What compiler do you and other developers use? Are you using VS2005 yet?"
&lt;/P&gt;
&lt;P&gt;
To be honest, I don't know what compiler I use.
&lt;/P&gt;
&lt;P&gt;
There is a separate part of the team that worries about things like
"What compiler should we use?"
They deal with nitty-gritty details like
"What version of the compiler should we use and what optimizations
should we enable?"
as well as higher-level planning like
"How are we going to organize our source code so that different parts
of the project can take advantage of each others' work while still
not requiring all members of the Windows team to compile
the entire operating system from scratch when they want to test
their changes?"
&lt;/P&gt;
&lt;P&gt;
I am not a member of that team,
nor am I invited to their meetings,
nor would I be interested in attending their meetings.
I'm perfectly happy to let them make these decisions.
They pick a compiler version and add it to the
toolset that gets installed to your computer when you
enlist in the Windows project.
That way nobody needs to care what version, service pack,
and patch number of the compiler they need to obtain.
It just comes with the development environment.
&lt;/P&gt;
&lt;P&gt;
As I've noted in
&lt;A HREF="http://technet.microsoft.com/en-us/magazine/cc742531.aspx"&gt;
an earlier column in &lt;I&gt;TechNet Magazine&lt;/I&gt;&lt;/A&gt;,
the operating systems division will at times call upon the languages
division to produce a special &lt;I&gt;not-found-in-nature&lt;/I&gt;
version of the compiler in order to satisfy a specific need.
Windows (at least the 32-bit version)
contains a 16-bit emulator and a miniature copy of 16-bit Windows.
Since no modern version of Visual Studio targets 16-bit Windows any more,
the compilers that the Windows team uses for 16-bit Windows necessarily
must come from somewhere else.
&lt;/P&gt;
&lt;P&gt;
Changing the compiler version is a risky operation,
because doing so will most likely expose subtle bugs in the code
which erroneously relied upon unspecified behavior,
such as order of evaluation or the location of memory barriers.
Not the sort of thing you want to spring on a project one week
before
&lt;A HREF="http://blogs.msdn.com/oldnewthing/archive/2008/08/26/8896167.aspx"&gt;
pencils down&lt;/A&gt;.
Yes, if all the code were written perfectly, then this wouldn't be a problem.
But few people write perfect code.
&lt;P&gt;
(And just as a favor to you,
I dug through the source code history for Windows and requested the
32-bit native compiler that was in use on August 28, 2006.
And then I extracted the version strings and compared it to the
version strings that came with Visual Studio&amp;nbsp;8,
and they seemed to match.
So I guess it's Visual Studio&amp;nbsp;8.
What relationship that has to VS2005 I don't know.)
&lt;/P&gt;
&lt;img src="http://blogs.msdn.com/aggbug.aspx?PostID=9939423" width="1" height="1"&gt;</content><author><name>oldnewthing</name><uri>http://blogs.msdn.com/members/oldnewthing.aspx</uri></author><category term="Other" scheme="http://blogs.msdn.com/oldnewthing/archive/tags/Other/default.aspx" /></entry><entry><title>The economic inefficiency of gift-giving</title><link rel="alternate" type="text/html" href="http://blogs.msdn.com/oldnewthing/archive/2009/12/18/9938500.aspx" /><id>http://blogs.msdn.com/oldnewthing/archive/2009/12/18/9938500.aspx</id><published>2009-12-18T15:00:01Z</published><updated>2009-12-18T15:00:01Z</updated><content type="html">&lt;P&gt;
Economist Joel Waldfogel explains
&lt;A HREF="http://www.npr.org/blogs/money/2009/11/podcast_happy_efficent_holiday.html"&gt;
why gift-giving is bad for the economy&lt;/A&gt;,
and why a charity gift card is the best luxury gift of all.
&lt;/P&gt;
&lt;P&gt;
He goes into more detail in his new book,
&lt;A HREF="http://www.amazon.com/dp/0691142645?tag=tholneth-20"&gt;
&lt;I&gt;Scroogenomics&lt;/I&gt;&lt;/A&gt;,
which you can buy somebody for Christmas just to tell Waldfogel where
he can stick it.
("In the bank!" he'll say as he heads out with his royalty check.)
&lt;/P&gt;
&lt;P&gt;
&lt;B&gt;Related&lt;/B&gt;:
Economist Tim Harford writes an advice column called
&lt;A HREF="http://timharford.com/articles/deareconomist/"&gt;
&lt;I&gt;Dear Economist&lt;/I&gt;&lt;/A&gt; for the
&lt;A HREF="http://www.ft.com/arts/columnists/timharford"&gt;
Financial Times&lt;/A&gt;.
But instead of applying economic theory to economic problems,
he applies economic theory to personal problems.
&lt;/P&gt;
&lt;UL&gt;
&lt;LI&gt;&lt;A HREF="http://timharford.com/2009/10/should-i-reveal-my-colourful-past/"&gt;
    How much information about myself should I reveal to the guy
    I'm interested in&lt;/A&gt;?
&lt;LI&gt;&lt;A HREF="http://timharford.com/2006/01/my-best-friends-wedding/"&gt;
    Should I cut my eight-month vacation in half
    in order to attend my best friend's wedding&lt;/A&gt;?
&lt;/UL&gt;
&lt;P&gt;
As Harford himself explains,
"Every advice columnist needs a persona,
and for &lt;I&gt;Dear Economist&lt;/I&gt;
&lt;A HREF="http://timharford.com/2009/09/the-unexpected-advice-columnist/"&gt;
it was blunt,
rude, and rather fond of the latest economic research&lt;/A&gt;."
&lt;/P&gt;
&lt;img src="http://blogs.msdn.com/aggbug.aspx?PostID=9938500" width="1" height="1"&gt;</content><author><name>oldnewthing</name><uri>http://blogs.msdn.com/members/oldnewthing.aspx</uri></author><category term="Non-Computer" scheme="http://blogs.msdn.com/oldnewthing/archive/tags/Non-Computer/default.aspx" /></entry><entry><title>I got an array with plenty of nuthin'</title><link rel="alternate" type="text/html" href="http://blogs.msdn.com/oldnewthing/archive/2009/12/18/9938499.aspx" /><id>http://blogs.msdn.com/oldnewthing/archive/2009/12/18/9938499.aspx</id><published>2009-12-18T15:00:00Z</published><updated>2009-12-18T15:00:00Z</updated><content type="html">&lt;P&gt;
A customer reported a memory leak in the function
&lt;CODE&gt;PropVariantClear&lt;/CODE&gt;:
&lt;/P&gt;
&lt;BLOCKQUOTE CLASS=q&gt;
&lt;P&gt;
We found the following memory leak in the function
&lt;CODE&gt;PropVariantClear&lt;/CODE&gt;.
Please fix it immediately because it causes our program to
run out of memory.
&lt;/P&gt;
&lt;P&gt;
If the &lt;CODE&gt;PROPVARIANT&lt;/CODE&gt;'s type is &lt;CODE&gt;VT_ARRAY&lt;/CODE&gt;,
then the corresponding &lt;CODE&gt;SAFEARRAY&lt;/CODE&gt; is leaked and not
cleaned up.
&lt;/P&gt;
&lt;PRE&gt;
SAFEARRAY* psa = SafeArrayCreateVector(VT_UNKNOWN, 0, 1);
PROPVARIANT v;
v.vt = VT_ARRAY;
v.parray = psa;
PropVariantClear(&amp;v);

// The psa is leaked
&lt;/PRE&gt;
&lt;P&gt;
Right now, we are temporarily working around this in our program
by inserting code before all calls to
&lt;CODE&gt;PropVariantClear&lt;/CODE&gt; to free the &lt;CODE&gt;SAFEARRAY&lt;/CODE&gt;,
but this is clearly an unsatisfactory solution
because it will merely result in double-free bugs once you fix
the bug.
Please give this defect your highest priority as it is holding up
deployment of our system.
&lt;/P&gt;
&lt;/BLOCKQUOTE&gt;
&lt;P&gt;
The &lt;CODE&gt;VT_ARRAY&lt;/CODE&gt; value is not a variant type in and of itself;
it is a type &lt;I&gt;modifier&lt;/I&gt;.
There are other type modifiers, such as
&lt;CODE&gt;VT_VECTOR&lt;/CODE&gt;
and &lt;CODE&gt;VT_BYREF&lt;/CODE&gt;.
The thing about modifiers is that they need to &lt;I&gt;modify something&lt;/I&gt;.
&lt;/P&gt;
&lt;BLOCKQUOTE CLASS=m&gt;
The line
&lt;CODE&gt;v.vt = VT_ARRAY&lt;/CODE&gt; is incorrect.
You have to say what you have a safe array &lt;I&gt;of&lt;/I&gt;.
In this case, you want &lt;CODE&gt;v.vt = VT_ARRAY | VT_UNKNOWN&lt;/CODE&gt;.
Once you change that, you'll find the memory leak is fixed.
&lt;/BLOCKQUOTE&gt;
&lt;P&gt;
The customer didn't believe this explanation.
&lt;/P&gt;
&lt;BLOCKQUOTE CLASS=q&gt;
&lt;P&gt;
I find this doubtful for several reasons.
&lt;/P&gt;
&lt;OL&gt;
&lt;LI&gt;While this would explain why the
    &lt;CODE&gt;IUnknown&lt;/CODE&gt;s in the &lt;CODE&gt;SAFEARRAY&lt;/CODE&gt;
    are not released,
    it doesn't explain why the &lt;CODE&gt;SAFEARRAY&lt;/CODE&gt; itself is leaked.
&lt;LI&gt;The &lt;CODE&gt;SAFEARRAY&lt;/CODE&gt; already contains this information,
    so it should already know that destroying it entails releasing
    the &lt;CODE&gt;IUnknown&lt;/CODE&gt; pointers.
&lt;LI&gt;If I manually call &lt;CODE&gt;SafeArrayDestroy&lt;/CODE&gt;,
    then the &lt;CODE&gt;IUnknown&lt;/CODE&gt;s are correctly
    released, confirming point&amp;nbsp;2.
&lt;LI&gt;The function &lt;CODE&gt;SafeArrayDestroy&lt;/CODE&gt; is never called;
    that is the root cause of the problem.
&lt;/OL&gt;
&lt;/BLOCKQUOTE&gt;
&lt;P&gt;
The customer's mental model of &lt;CODE&gt;PropVariantDestroy&lt;/CODE&gt;
appeared to be that it should go something like this:
&lt;/P&gt;
&lt;PRE&gt;
if (pvt-&amp;gt;vt &amp;amp; VT_ARRAY) {
 switch (pvt-&amp;gt;vt &amp;amp; VT_TYPEMASK) {
 ...
 case VT_UNKNOWN:
  ... release the IUnknowns in the SAFEARRAY...
  break;
 ...
 }
 InternalFree(pvt-&amp;gt;psa-&amp;gt;pvData);
 InternalFree(pvt-&amp;gt;psa);
 return S_OK;
}
&lt;/PRE&gt;
&lt;P&gt;
In fact what's really going on is that the value of
&lt;CODE&gt;VT_ARRAY&lt;/CODE&gt; is interpreted as
&lt;CODE&gt;VT_ARRAY | VT_EMPTY&lt;/CODE&gt;,
because (1)&amp;nbsp;&lt;CODE&gt;VT_ARRAY&lt;/CODE&gt; is a modifier,
so it has to modify something, and (2)&amp;nbsp;the
numeric value of zero happens to be equal to &lt;CODE&gt;VT_EMPTY&lt;/CODE&gt;.
In other words, you told OLE automation that your &lt;CODE&gt;PROPVARIANT&lt;/CODE&gt;
holds a &lt;CODE&gt;SAFEARRAY&lt;/CODE&gt; filled with &lt;CODE&gt;VT_EMPTY&lt;/CODE&gt;.
&lt;/P&gt;
&lt;P&gt;
It also happens that a &lt;CODE&gt;SAFEARRAY&lt;/CODE&gt; of &lt;CODE&gt;VT_EMPTY&lt;/CODE&gt;
is illegal.
Only certain types can be placed in a &lt;CODE&gt;SAFEARRAY&lt;/CODE&gt;,
and &lt;CODE&gt;VT_EMPTY&lt;/CODE&gt; is not one of them.
&lt;/P&gt;
&lt;P&gt;
The call to &lt;CODE&gt;PropVariantClear&lt;/CODE&gt; was returning the
error
&lt;CODE&gt;DISP_E_BADVARTYPE&lt;/CODE&gt;.
It was performing parameter validation and rejecting the property
variant as invalid,
because you can't have an array of nothing.
The customer's response to this explanation was very terse.
&lt;/P&gt;
&lt;BLOCKQUOTE CLASS=q&gt;
Tx. Interesting.
&lt;/BLOCKQUOTE&gt;
&lt;img src="http://blogs.msdn.com/aggbug.aspx?PostID=9938499" width="1" height="1"&gt;</content><author><name>oldnewthing</name><uri>http://blogs.msdn.com/members/oldnewthing.aspx</uri></author><category term="Code" scheme="http://blogs.msdn.com/oldnewthing/archive/tags/Code/default.aspx" /></entry><entry><title>Surprising things injected into Mozart cadenzas</title><link rel="alternate" type="text/html" href="http://blogs.msdn.com/oldnewthing/archive/2009/12/17/9937976.aspx" /><id>http://blogs.msdn.com/oldnewthing/archive/2009/12/17/9937976.aspx</id><published>2009-12-17T15:00:01Z</published><updated>2009-12-17T15:00:01Z</updated><content type="html">&lt;P&gt;
&lt;A HREF="http://seattletimes.nwsource.com/html/thearts/2003976945_symp27.html"&gt;
This review of a Seattle Symphony concert from 2007&lt;/A&gt;
mentioned that back in 1998, soloist Jon Kimura Parker inserted the
theme from &lt;I&gt;The X-Files&lt;/I&gt; into one of his cadenzas.
Cadenzas were originally points in a concerto
at which soloists could improvise
and show off their technical skills,
but over the years,
the contents of cadenzas have become more and more rehearsed,
with most composers having switched over to fully-written-out
cadenzas over a hundred years ago.
&lt;/P&gt;
&lt;P&gt;
That's why it's so exciting when an improvised cadenza reappears
on the scene.
All of a sudden, &lt;I&gt;anything can happen&lt;/I&gt;.
Reading the article reminded me of a cadenza surprise
in a performance by Awadagin Pratt nearly twenty years ago.
I'm fairly certain the piece was a Mozart piano concerto,
and during the cadenza,
Pratt slipped into a middle voice
the theme from the opening movement of the Mendelssohn
Scottish Symphony,
which was the next piece on the program!
By the time I figured out what was happening, it was over.
My opportunity to burst into applause in the middle of a piece was lost.
&lt;/P&gt;
&lt;img src="http://blogs.msdn.com/aggbug.aspx?PostID=9937976" width="1" height="1"&gt;</content><author><name>oldnewthing</name><uri>http://blogs.msdn.com/members/oldnewthing.aspx</uri></author><category term="Non-Computer" scheme="http://blogs.msdn.com/oldnewthing/archive/tags/Non-Computer/default.aspx" /></entry><entry><title>What was the ShowCursor function intended to be used for?</title><link rel="alternate" type="text/html" href="http://blogs.msdn.com/oldnewthing/archive/2009/12/17/9937972.aspx" /><id>http://blogs.msdn.com/oldnewthing/archive/2009/12/17/9937972.aspx</id><published>2009-12-17T15:00:00Z</published><updated>2009-12-17T15:00:00Z</updated><content type="html">&lt;P&gt;
Back in the days when Windows was introduced,
a mouse was a fancy newfangled gadget
which not everybody had on their machine.
Windows acknowledged this and supported systems without
a mouse by having keyboard accelerators for everything
(or at least that was the intent).
But if the design stopped there, you'd have a dead cursor
in the middle of your screen all the time,
which you could move around if you had a mouse,
which you didn't.
&lt;/P&gt;
&lt;P&gt;
Enter the &lt;CODE&gt;ShowCursor&lt;/CODE&gt; function.
&lt;/P&gt;
&lt;P&gt;
The &lt;CODE&gt;ShowCursor&lt;/CODE&gt; function takes a parameter
that indicates whether you want to show or hide the cursor.
(It would perhaps be more verbosely named
&lt;CODE&gt;ChangeCursorShowState&lt;/CODE&gt;.)
If you call &lt;CODE&gt;ShowCursor(TRUE)&lt;/CODE&gt; then the cursor
show count is incremented by one;
if you call &lt;CODE&gt;ShowCursor(FALSE)&lt;/CODE&gt; then the cursor
show count is decremented by one.
A cursor is show on the screen if the cursor show count is greater
than or equal to zero.
&lt;/P&gt;
&lt;P&gt;
When Windows starts up, it checks if you have a mouse.
If so, then the cursor show count is initialized to zero;
otherwise, it is initialized to negative one.
That way, you don't get an annoying immovable cursor on the screen
if you don't have a mouse.
&lt;/P&gt;
&lt;P&gt;
If a program entered a state where it wanted to show the cursor
even on systems without a mouse, it would call
&lt;CODE&gt;ShowCursor(TRUE)&lt;/CODE&gt; when it entered the state,
and
&lt;CODE&gt;ShowCursor(FALSE)&lt;/CODE&gt; when it left it.
One such state might be when activating the keyboard interface
for selecting a rectangular region in a document.
Under these conditions, a program naturally is expected to
&lt;A HREF="http://blogs.msdn.com/oldnewthing/archive/2007/07/06/3716170.aspx#3838293"&gt;
move the cursor around in response to user actions&lt;/A&gt;,
even if the user didn't move the physical mouse hardware.
&lt;/P&gt;
&lt;P&gt;
But the most common reason for forcing the cursor to be shown
is in order to show an hourglass cursor because it's busy.
That's right, back in the mouseless days, code to display
an hourglass cursor went like this:
&lt;PRE&gt;
HCURSOR hcurPrev = SetCursor(LoadCursor(NULL, IDC_WAIT));
&lt;FONT COLOR=blue&gt;ShowCursor(TRUE); // force cursor shown on mouseless systems&lt;/FONT&gt;
... perform long operation ...
&lt;FONT COLOR=blue&gt;ShowCursor(FALSE); // re-hide cursor on mouseless systems&lt;/FONT&gt;
SetCursor(hcurPrev);
&lt;/PRE&gt;
&lt;P&gt;
Conversely, if a program entered a state where it wanted to hide
the cursor even on systems with a mouse, it would call
&lt;CODE&gt;ShowCursor(FALSE)&lt;/CODE&gt; when it entered the state,
and
&lt;CODE&gt;ShowCursor(TRUE)&lt;/CODE&gt; when it left it.
For example, you might do this when showing a slide show.
&lt;/P&gt;
&lt;P&gt;
Let's look at how this all worked out in practice.
I use a table because people seem to like tables.
&lt;/P&gt;
&lt;TABLE STYLE="border-collapse: collapse"&gt;
&lt;TR&gt;
    &lt;TD STYLE="border: solid .75pt black"&gt;&lt;/TD&gt;
    &lt;TH STYLE="border: solid .75pt black"&gt;Machine with mouse&lt;/TH&gt;
    &lt;TH STYLE="border: solid .75pt black"&gt;Machine without mouse&lt;/TH&gt;
&lt;/TR&gt;
&lt;TR&gt;
    &lt;TD STYLE="border: solid .75pt black"&gt;Normal&lt;/TD&gt;
    &lt;TD ALIGN=right STYLE="border: solid .75pt black"&gt;0 (cursor shown)&lt;/TD&gt;
    &lt;TD ALIGN=right STYLE="border: solid .75pt black"&gt;-1 (cursor hidden)&lt;/TD&gt;
&lt;/TR&gt;
&lt;TR&gt;
    &lt;TH COLSPAN=3 STYLE="border: solid .75pt black"&gt;Enter mode where cursor should be forced shown&lt;/TH&gt;
&lt;/TR&gt;
&lt;TR&gt;
    &lt;TD STYLE="border: solid .75pt black"&gt;&lt;CODE&gt;ShowCursor(TRUE)&lt;/CODE&gt;&lt;/TD&gt;
    &lt;TD ALIGN=right STYLE="border: solid .75pt black"&gt;1 (cursor shown)&lt;/TD&gt;
    &lt;TD ALIGN=right STYLE="border: solid .75pt black"&gt;0 (cursor shown)&lt;/TD&gt;
&lt;/TR&gt;
&lt;TR&gt;
    &lt;TH COLSPAN=3 STYLE="border: solid .75pt black"&gt;Exit mode where cursor should be forced shown&lt;/TH&gt;
&lt;/TR&gt;
&lt;TR&gt;
    &lt;TD STYLE="border: solid .75pt black"&gt;&lt;CODE&gt;ShowCursor(FALSE)&lt;/CODE&gt;&lt;/TD&gt;
    &lt;TD ALIGN=right STYLE="border: solid .75pt black"&gt;0 (cursor shown)&lt;/TD&gt;
    &lt;TD ALIGN=right STYLE="border: solid .75pt black"&gt;-1 (cursor hidden)&lt;/TD&gt;
&lt;/TR&gt;
&lt;TR&gt;
    &lt;TH COLSPAN=3 STYLE="border: solid .75pt black"&gt;Enter mode where cursor should be forced hidden&lt;/TH&gt;
&lt;/TR&gt;
&lt;TR&gt;
    &lt;TD STYLE="border: solid .75pt black"&gt;&lt;CODE&gt;ShowCursor(FALSE)&lt;/CODE&gt;&lt;/TD&gt;
    &lt;TD ALIGN=right STYLE="border: solid .75pt black"&gt;-1 (cursor hidden)&lt;/TD&gt;
    &lt;TD ALIGN=right STYLE="border: solid .75pt black"&gt;-2 (cursor hidden)&lt;/TD&gt;
&lt;/TR&gt;
&lt;TR&gt;
    &lt;TH COLSPAN=3 STYLE="border: solid .75pt black"&gt;Exit mode where cursor should be forced hidden&lt;/TH&gt;
&lt;/TR&gt;
&lt;TR&gt;
    &lt;TD STYLE="border: solid .75pt black"&gt;&lt;CODE&gt;ShowCursor(TRUE)&lt;/CODE&gt;&lt;/TD&gt;
    &lt;TD ALIGN=right STYLE="border: solid .75pt black"&gt;0 (cursor shown)&lt;/TD&gt;
    &lt;TD ALIGN=right STYLE="border: solid .75pt black"&gt;-1 (cursor hidden)&lt;/TD&gt;
&lt;/TR&gt;
&lt;/TABLE&gt;
&lt;P&gt;
Now that all systems come with a mouse as standard equipment,
this historical information is not of much use,
but there it is in case you were wondering.
(And in a case of &lt;I&gt;everything old is new again&lt;/I&gt;,
the growing popularity of touch computing means that
you once again have a class of computers with no mouse.
So maybe this information is useful after all.
&lt;A HREF="http://blogs.msdn.com/oldnewthing/archive/2009/10/28/9913810.aspx"&gt;
Just a fluke, I assure you&lt;/A&gt;.)
&lt;/P&gt;
&lt;P&gt;
Back in the old 16-bit days,
this counter was a global state,
along with other window manager states like the focus window
and the input queue.
During the conversion to Win32,
the cursor show counter became a thread-local state.
(Naturally,
multiple threads could merge their cursor show counters
by attachment.)
Consequently, when a thread calls &lt;CODE&gt;ShowCursor&lt;/CODE&gt;
it affects the cursor show state only for windows that
belong to that thread.
&lt;/P&gt;
&lt;img src="http://blogs.msdn.com/aggbug.aspx?PostID=9937972" width="1" height="1"&gt;</content><author><name>oldnewthing</name><uri>http://blogs.msdn.com/members/oldnewthing.aspx</uri></author><category term="History" scheme="http://blogs.msdn.com/oldnewthing/archive/tags/History/default.aspx" /></entry></feed>