|
dev
newsgroups
|
|||||||||||||||||||||||
|
|||||||||||||||||||||||
Semantics of BeginXyz()...EndXyz()I'm designing a system for communicating with an USB device. Now I'm a bit stuck with Microsoft's asynchronous operation concept in .NET. You know, the stuff with a normal method (eg. Receive()) and two asynchronous methods (eg. BeginReceive() and EndReceive()). Now I'm wondering about the exact semantics of this concept. Maybe someone with more experience can help me answer these questions: - What happens if an error occurs during the asynchronous transmission? Is it reported by EndReceive()? - Do IAsyncResult.AsyncWaitHandle and IsCompleted both need to be set regardless of the outcome of the operation? - What about multiple simultaneous calls to BeginReceive()? Is this allowed? Or can I decided whether to support it on a case-per-case basis? Thanks, -Markus- Hello, Markus!
ME> I'm designing a system for communicating with an USB device. Now I'm a ME> bit stuck with Microsoft's asynchronous operation concept in .NET. You ME> know, the stuff with a normal method (eg. Receive()) and two ME> asynchronous methods (eg. BeginReceive() and EndReceive()). ME> Now I'm wondering about the exact semantics of this concept. Maybe ME> someone with more experience can help me answer these questions: ME> - What happens if an error occurs during the asynchronous transmission? ME> Is it reported by EndReceive()? Yes, it can be reported via throwing an exception on EndReceive(...), or with an out parameter in EndReceive(...) ME> - Do IAsyncResult.AsyncWaitHandle and IsCompleted both need to be set ME> regardless of the outcome of the operation? From the docs: " Notes to Implementers The object that implements IAsyncResult does not need to create the WaitHandle until the AsyncWaitHandle property is read. It is the choice of the IAsyncResult implementer. However, if the implementer creates AsyncWaitHandle, it is the responsibility of the implementer to signal the WaitHandle that will terminate the wait at the appropriate time. For example, System.Runtime.Remoting.Messaging.AsyncResult terminates the wait on behalf of the caller when an asynchronously invoked method returns. Once created, AsyncWaitHandle should be kept alive until the user calls the method that concludes the asynchronous operation. At that time the object behind AsyncWaitHandle can be discarded. " So, AsyncWaitHandle and IsCompleted need to be set as callers will excepect appropriate (documented) behavior . ME> - What about multiple simultaneous calls to BeginReceive()? Is this ME> allowed? Yes, every call to BeginReceive will spawn ( get thread from threadpool ) new thread. However, callers typically will call BeginReceive/EndReceive sequentially ME> Or can I decided whether to support it on a case-per-case basis? You mean to block BeginReceive until previous operation is completed? If so, then BeginReceive will be the same as Receive... Vadym Stetsyak wrote:
> Hello, Markus! Hm, it makes sense, but I've never seen that described anywhere. Do you > > ME> - What happens if an error occurs during the asynchronous transmission? > ME> Is it reported by EndReceive()? > > Yes, it can be reported via throwing an exception on EndReceive(...), or with an out parameter in EndReceive(...) indidentally still happen to know where you found that? > Alright, gues I overlooked that paragraph, sorry ;)> ME> - Do IAsyncResult.AsyncWaitHandle and IsCompleted both need to be set > ME> regardless of the outcome of the operation? > > From the docs: > [...] > I had planned on adding a timeout argument to the Receive() method, but > So, AsyncWaitHandle and IsCompleted need to be set as callers will excepect appropriate (documented) behavior . > > ME> - What about multiple simultaneous calls to BeginReceive()? Is this > ME> allowed? > > Yes, every call to BeginReceive will spawn ( get thread from threadpool ) new thread. > However, callers typically will call BeginReceive/EndReceive sequentially > > ME> Or can I decided whether to support it on a case-per-case basis? > You mean to block BeginReceive until previous operation is completed? If so, then BeginReceive will be the same as Receive... I guess that probably wasn't such a good idea after all. As I understand it now, Receive() is supposed to return immediately. If less than the requested number of bytes is available, only that much data is returned, just like the Stream.Read() methods. Thanks, -Markus- Hello, Markus!
ME> Hm, it makes sense, but I've never seen that described anywhere. Do you ME> indidentally still happen to know where you found that? As an example of such behavior consider async socket operations. Socket.BeginReceive/EndReceive ME> I had planned on adding a timeout argument to the Receive() method, but ME> I guess that probably wasn't such a good idea after all. As I ME> understand it now, Receive() is supposed to return immediately. If less ME> than the requested number of bytes is available, only that much data is ME> returned, just like the Stream.Read() methods. Yes, Receive returns immediately if data is available, it returns number of received data, if there is no data - it blocks...
Other interesting topics
|
|||||||||||||||||||||||