Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

Q: I/O compl port mysterious failure

52 views
Skip to first unread message

Jeremy

unread,
Jun 27, 2001, 9:37:30 PM6/27/01
to
Friends,

I'm getting this error on GetQueuedCompletionStatus:

code 33 - The process cannot access the file because another process has
locked a portion of the file.

It's a wait on a ConnectEx'ed socket. No connections are attempted by
the time of the failure. Any ideas on how to interpret this thing?

Jeremy

unread,
Jun 27, 2001, 10:18:22 PM6/27/01
to
An additional question: when connecting "devices" to the io compl port,
should the "completion keys" be unique for every device, or only the
combination of the key->devide handle be unique?

Maxim S. Shatskih

unread,
Jun 28, 2001, 9:00:01 AM6/28/01
to
> An additional question: when connecting "devices" to the io compl port,
> should the "completion keys" be unique for every device, or only the
> combination of the key->devide handle be unique?

From MSDN Library:

"A completion key is a per-file key that is specified in a call to
CreateIoCompletionPort. "

So, it is per-file, not per-device.

In fact, the notion of "device" for sockets is a bit strange. All TCP/IP
sockets are files opened on \Device\Afd.

Max


Jeremy

unread,
Jun 28, 2001, 11:56:56 AM6/28/01
to
"Maxim S. Shatskih" wrote:
>
> > An additional question: when connecting "devices" to the io compl port,
> > should the "completion keys" be unique for every device, or only the
> > combination of the key->devide handle be unique?
>
> From MSDN Library:
>
> "A completion key is a per-file key that is specified in a call to
> CreateIoCompletionPort. "
>
> So, it is per-file, not per-device.
I was under the impression that "file" and "device" are one and the same
in that context. What I was wondering about was whether there can be
duplicates among the registered "completion keys". I kinda feel there
shouldn't be any... I guess I see some ambiguity in this data
piece--completion key--I'm not sure what it's for. All data I need I can
supply inside the OVERLAPPED-based chunk...

Sean Kelly

unread,
Jun 28, 2001, 12:01:31 PM6/28/01
to
"Jeremy" <jeremyk.r...@privacy.nu> wrote in message
news:3B3B53C8...@privacy.nu...

> "Maxim S. Shatskih" wrote:
> >
> > > An additional question: when connecting "devices" to the io compl
port,
> > > should the "completion keys" be unique for every device, or only the
> > > combination of the key->devide handle be unique?
> >
> > From MSDN Library:
> >
> > "A completion key is a per-file key that is specified in a call to
> > CreateIoCompletionPort. "
> >
> > So, it is per-file, not per-device.
> I was under the impression that "file" and "device" are one and the same
> in that context. What I was wondering about was whether there can be
> duplicates among the registered "completion keys".

I don't see why not. I think it's just a pointer the iocp process passes
through, no constraints are placed on it.

> I kinda feel there
> shouldn't be any... I guess I see some ambiguity in this data
> piece--completion key--I'm not sure what it's for. All data I need I can
> supply inside the OVERLAPPED-based chunk...

See your other iocp thread... Until today I was doing what you're doing --
storing everything in the overlapped struct. But after reading the thread
it occurred to me that since I use a single class instance to handle all the
communications for a given socket, that I may as well use the key for a
pointer to the class rather than storing it in the overlapped struct. It
seems cleaner that way.

Sean


Jeremy

unread,
Jun 28, 2001, 12:40:21 PM6/28/01
to
Well, the reason I'm banging on it is that in one context my GQCS fails
(whereas in a few pilot apps it doesn't -- in nearly the same context.)
So, I'm trying to see what the causes could be here. The func returns
null, yet the last error is "operation completed successfully" <G>. I'll
be darned ...

Sean Kelly

unread,
Jun 28, 2001, 10:12:49 PM6/28/01
to
"Jeremy" <jeremyk.r...@privacy.nu> wrote in message
news:3B3B5DF5...@privacy.nu...

Well, just to clear up the issue about the key, I changed my code today.
You are allowed a key per socket, when you call CreateIOCompletionPort. I
pulled my object pointer out of the overlapped struct and replaced it with
the key instead and everything worked exactly the same. So... I doubt
that's your problem.

Sean


Andy Walldorff

unread,
Jun 29, 2001, 8:27:16 AM6/29/01
to
Do you mean GQCS fails and the OVERLAPPED structure is NULL? It sounds like
you've closed the IOCP.

Jeremy <jeremyk.r...@privacy.nu> wrote in message

news:3B3B5DF5...@privacy.nu...

Jeremy

unread,
Jun 29, 2001, 12:31:18 PM6/29/01
to
Andy Walldorff wrote:
>
> Do you mean GQCS fails and the OVERLAPPED structure is NULL? It sounds like
> you've closed the IOCP.
No, it isn't <g>. That's the whole point, the OVL-based work packet
comes in fine. I don't think the port is at fault here, it's something
with the socket or the way I ship to the iocp. But AcceptEx doesn't fail
! (Actually it does, but with the IO_Pending thing, so that's what I
want.) Now, I just picked a response (on the winsock ng), some guy told
me the OVL->Internal holds the driver's error code, and in my case it's
STATUS_CANCELLED. Why would this thing get cancelled? The funny thing
is, I have a bare-bones pilot to test out this mechanism and it works!!!
Almost identical code, maybe one fewer thread. That shouldn't matter,
should it?

Jeremy

unread,
Jun 29, 2001, 10:01:08 PM6/29/01
to
Found it! Turns out if the thread that called AcceptEx exits, the i/o
request will be cancelled. No mention in any documentation I can think
of, no apparent reason why it should act like that either. Go figure.

I would understand that if I used completion routines, but with the
iocp, who cares who issued a request?

Any thoughts on that? Is that some kind of a known glitch?

Sean Kelly

unread,
Jun 30, 2001, 12:02:27 AM6/30/01
to
"Jeremy" <jeremyk.r...@privacy.nu> wrote in message
news:3B3D32E4...@privacy.nu...

I'm shocked. Is it possible that some aspect of your overlapped struct,
etc. is being freed when the one thread exits? Like was it allocated via
thread local memory, on the stack, etc?

Sean


Tomas Restrepo

unread,
Jun 30, 2001, 9:56:50 AM6/30/01
to
Hi Jeremy,

It's a known issue with NT's IO subsystem. Check out this link for some more
information:
http://groups.google.com/groups?q=Completion+Port+Thread+Cancel+group:micros
oft.public.win32.programmer.kernel&hl=en&safe=off&rnum=1&ic=1&selm=%23JNDAcX
Q%24GA.292%40cppssbbsa04

(watch for breaks, really long URL).

--
Tomas Restrepo
tom...@mvps.org


Jeff Henkels

unread,
Jun 30, 2001, 10:22:01 AM6/30/01
to
A tip for the future -- if you enclose long URLs in <>, most newsreaders
will use the entire URL for the link, which makes things much easier.

e.g.
<http://groups.google.com/groups?q=Completion+Port+Thread+Cancel+group:micro
soft.public.win32.programmer.kernel&hl=en&safe=off&rnum=1&ic=1&selm=%23JNDAc
XQ%24GA.292%40cppssbbsa04>


"Tomas Restrepo" <tom...@mvps.org> wrote in message
news:eHZt7xWABHA.1768@tkmsftngp03...

William DePalo [MVP]

unread,
Jun 30, 2001, 10:47:10 AM6/30/01
to
"Jeff Henkels" <je...@mapson.privatemail.com> wrote in message
news:Ddl%6.164512$Mq.49...@e420r-sjo3.usenetserver.com...

> A tip for the future -- if you enclose long URLs in <>, most newsreaders
> will use the entire URL for the link, which makes things much easier.
>
> e.g.
>
<http://groups.google.com/groups?q=Completion+Port+Thread+Cancel+group:micro
>
soft.public.win32.programmer.kernel&hl=en&safe=off&rnum=1&ic=1&selm=%23JNDAc
> XQ%24GA.292%40cppssbbsa04>

FWIW: If that's what you've done above, It doesn't work in Outlook Express.

Regards,
Will

Maxim S. Shatskih

unread,
Jun 30, 2001, 8:32:11 AM6/30/01
to
> I would understand that if I used completion routines, but with the
> iocp, who cares who issued a request?

Yes, really so.

Any pending Win32 IO requests will be cancelled on thread termination. Any.
Regardless of whether you use completion ports or not. FILE_FLAG_OVERLAPPED
will only give you the ability of not waiting inside ReadFile etc. for the
request to complete. Nevertheless, even these requests will be cancelled on
thread death.

This is how NT IO subsystem works.

As about AcceptEx - it is just a DeviceIoControl to afd.sys, the same IO
manager semantics applied to it too.

Max


James Antognini

unread,
Jun 30, 2001, 3:55:22 PM6/30/01
to
I just tried it with Netscape Communicator, and your URL didn't work
that way.

--
James Antognini
IBM Watson Research


Bruce Chastain

unread,
Jul 2, 2001, 11:22:22 AM7/2/01
to
"Jeff Henkels" <je...@mapson.privatemail.com> wrote in message
news:Ddl%6.164512$Mq.49...@e420r-sjo3.usenetserver.com...
> A tip for the future -- if you enclose long URLs in <>, most newsreaders
> will use the entire URL for the link, which makes things much easier.
>
> e.g.
>
<http://groups.google.com/groups?q=Completion+Port+Thread+Cancel+group:micro
>
soft.public.win32.programmer.kernel&hl=en&safe=off&rnum=1&ic=1&selm=%23JNDAc
> XQ%24GA.292%40cppssbbsa04>

Didn't work here with OE and IE either.

Bruce.

Jeremy

unread,
Jul 3, 2001, 1:38:57 PM7/3/01
to
Nope, the memory's all right (the OVL-thing floats peacefully to the
iocp, no problem here, it's just it carries the news of a cancelled io
request <g>.) That's how it works. Someone on another ng told me that io
completions are returned by the kernel by filing a kernel APC regardless
of whether they're are destined to the user APC or a iocp. I find it
funny that there's no mention of this "feature" anywhere.


>
> Sean

Jeremy

unread,
Jul 3, 2001, 1:40:29 PM7/3/01
to
How the hell you know all this stuff. Awesome.


>
> Max

Jeremy

unread,
Jul 3, 2001, 1:41:00 PM7/3/01
to
Tomas Restrepo wrote:
> It's a known issue with NT's IO subsystem. Check out this link for some more
> information:
> http://groups.google.com/groups?q=Completion+Port+Thread+Cancel+group:micros
> oft.public.win32.programmer.kernel&hl=en&safe=off&rnum=1&ic=1&selm=%23JNDAcX
> Q%24GA.292%40cppssbbsa04
>
> (watch for breaks, really long URL).
Got it! Precisely my case, thanks.

>
> --
> Tomas Restrepo
> tom...@mvps.org

Jeremy

unread,
Jul 3, 2001, 1:43:39 PM7/3/01
to
James Antognini wrote:
>
> I just tried it with Netscape Communicator, and your URL didn't work
> that way.
Worked for me. Anyway, here it is:
<http://groups.google.com/groups?q=Completion+Port+Thread+Cancel+group:microsoft.public.win32.programmer.kernel&hl=en&safe=off&rnum=1&ic=1&selm=%23JNDAcXQ%24GA.292%40cppssbbsa04>

From: Slava M. Usov (stripit...@usa.net)
Subject: Re: WSA IO with IOCPs depends on calling thread!!?
Newsgroups: microsoft.public.win32.programmer.networks,
microsoft.public.win32.programmer.kernel
Date: 1999/12/08


Alen Ilkov <al...@entera.com> wrote in message
news:uJXOTLOQ$GA.238@cppssbbsa05...
> As Jeff Fink pointed out, if you call a WSA async func and rely on a IO
> completion port for the result, whenever the calling thread exits,
> GetQueuedCompletionStatus fails.
>
> GetLastError( ) returns error 995, which means "The I/O operation has been
> aborted because of either a thread exit or an application request."
>
> I've just tested it myself with a little console app (if anybody is
> interested I got the test code).
>
> Has anybody dealt with this problem and is it well-known? Is this by design
> and if yes then how, it seems totally counter-intuitive! I guess the best
> way to deal with this is have a worker thread that's always there post the
> read and when you want to do async IO from a thread that may dissapear, use
> PostQueuedCompletionStatus to ask a worker thread to make the call. A
> wrapped class could encapsulate all that.
>
> Any input is appreciated.

We have discussed this issue [I'm not sure we can call it a problem] in this
newsgroup, although a long time ago. The thread was named "Cancelling
non-overlapped pipe I/O" Try deja to find it. This discussion was, however,
centered around a bug in CancelIo() [or, actually, on an undocumented
feature of it], so I'll explain shortly.

When a thread submits an IO request, regardless of the type of the request
[synchronous, asynchronous, asynchronous with IOCP], IO manager assigns the
resulting IRP [IO Request Packet] to the thread... when the thread is
terminated [or terminates], IO manager is notified and tries to cancel all
of the IRPs assigned to the thread.

An IRP *must* be associated with a thread, because the final phase of IRP
processing is an APC [Asynchronous Procedure Call] sent to the initiating
thread.

While in the context of IOCP this APC can be sent to any of the threads that
have attached to the IOCP, IO manager is not smart enough to do so... and
perhaps it does not have to be this smart, because it's not very difficult
to keep the thread alive until all of the requests have been completed. BTW,
why in IOCP scenario do you have threads that disappear? If anything, *this*
is counter-intuitive.

--

Slava

Please send any replies to this newsgroup.
microsoft.public.win32.programmer.kernel

Maxim S. Shatskih

unread,
Jul 4, 2001, 11:00:25 AM7/4/01
to
> > As about AcceptEx - it is just a DeviceIoControl to afd.sys, the same IO
> > manager semantics applied to it too.
> How the hell you know all this stuff. Awesome.

Pass this by the debugger.

Max


0 new messages