Solved

C# to VB.NET 2008 - 2 lines code equivalent

Posted on 2010-08-18
7
544 Views
Last Modified: 2013-12-17
I am using the Microsoft TcpListener Class that can be found at these pages:

http://www.koders.com/csharp/fid69A4DDD88271AE50AEF9DFA83EDB65919FB807EA.aspx
http://msdn.krugle.com/kse/entfiles/gdpe/codeplex.com/scmi_17301/fx/src/net/system/net/sockets/tcplistener.cs#1

Although, I have made a VB.NET 2008 translation of this C# code, I don't know an equivalent for C# LazyAsyncResult expression.

Below is the C# function:

public TcpClient EndAcceptTcpClient(IAsyncResult asyncResult){
    if(Logging.On)Logging.Enter(Logging.Sockets, this, "EndAcceptTcpClient", null);
    
    if (asyncResult == null)
    {
        throw new ArgumentNullException("asyncResult");
    }
    
    LazyAsyncResult lazyResult = asyncResult as LazyAsyncResult;
    Socket asyncSocket = lazyResult == null ? null : lazyResult.AsyncObject as Socket;
    if (asyncSocket == null)
    {
        throw new ArgumentException(SR.GetString(SR.net_io_invalidasyncresult), "asyncResult");
    }
    
    // This will throw ObjectDisposedException if Stop() has been called.
    Socket socket = asyncSocket.EndAccept(asyncResult);
    
    if(Logging.On)Logging.Exit(Logging.Sockets, this, "EndAcceptTcpClient", socket);
    return new TcpClient(socket);
}

Open in new window

0
Comment
Question by:mediasoftware
7 Comments
 
LVL 52

Expert Comment

by:Carl Tawn
ID: 33467103
A direct translation should be something like:

Dim lazyResult As LazyAsyncResult = CType(asyncResult, LazyAsyncResult)

Dim asyncSocket As Socket = IIf(lazyResult = Nothing, Nothing, CType(lazyResult.AsyncObject, Socket))

Open in new window

0
 

Author Comment

by:mediasoftware
ID: 33467112
I don't know an equivalent for C# LazyAsyncResult expression.

Below is VB.NET 2008 translation of this C# code:

Public Function EndAcceptTcpClient(ByVal asyncResult As IAsyncResult) As TcpClient
    If asyncResult Is Nothing Then
        Throw New ArgumentNullException("asyncResult")
    End If
    
    Dim lazyResult As LazyAsyncResult = TryCast(asyncResult, LazyAsyncResult)
    Dim asyncSocket As Socket = If(lazyResult Is Nothing, Nothing, TryCast(lazyResult.AsyncObject, Socket))
    If asyncSocket Is Nothing Then
        Throw New ArgumentException("Invalid AsyncResult", "asyncResult")
    End If
    
    ' This will throw ObjectDisposedException if Stop() has been called.
    Dim socket_Renamed As Socket = asyncSocket.EndAccept(asyncResult)
    
    Return New TcpClient1(socket_Renamed)
End Function

Open in new window

0
 
LVL 27

Expert Comment

by:nmarun
ID: 33467172
0
What Security Threats Are You Missing?

Enhance your security with threat intelligence from the web. Get trending threat insights on hackers, exploits, and suspicious IP addresses delivered to your inbox with our free Cyber Daily.

 
LVL 6

Accepted Solution

by:
PhilAI earned 500 total points
ID: 33467176
Is this what you were looking for?

'------------------------------------------------------------------------------
' <copyright file="_LazyAsyncResult.cs" company="Microsoft">
'     
'      Copyright (c) 2006 Microsoft Corporation.  All rights reserved.
'     
'      The use and distribution terms for this software are contained in the file
'      named license.txt, which can be found in the root of this distribution.
'      By using this software in any fashion, you are agreeing to be bound by the
'      terms of this license.
'     
'      You must not remove this notice, or any other, from this software.
'     
' </copyright>
'------------------------------------------------------------------------------

Imports System.Threading
Imports System.Diagnostics
Imports System.Collections
Namespace System.Net

	' LazyAsyncResult - Base class for all IAsyncResult classes
	' that want to take advantage of lazy allocated event handles
	Friend Class LazyAsyncResult
		Implements IAsyncResult
		Private Const c_HighBit As Integer = CInt(&H80000000UI)
		Private Const c_ForceAsyncCount As Integer = 50

		' This is to avoid user mistakes when they queue another async op from a callback the completes sync.
		<ThreadStatic> _
		Private Shared t_ThreadContext As ThreadContext

		Private Shared ReadOnly Property CurrentThreadContext() As ThreadContext
			Get
				Dim threadContext As ThreadContext = t_ThreadContext
				If threadContext Is Nothing Then
					threadContext = New ThreadContext()
					t_ThreadContext = threadContext
				End If
				Return threadContext
			End Get
		End Property

		Private Class ThreadContext
			Friend m_NestedIOCount As Integer
		End Class

		#If DEBUG Then
		Friend _DebugAsyncChain As Object
		Private _ProtectState As Boolean
		' Used by ContextAwareResult to prevent some calls.
		#End If

		'
		' class members
		'
		Private m_AsyncObject As Object
		' Caller's async object.
		Private m_AsyncState As Object
		' Caller's state object.
		Private m_AsyncCallback As AsyncCallback
		' Caller's callback method.
		Private m_Result As Object
		' Final IO result to be returned byt the End*() method.
		Private m_ErrorCode As Integer
		' Win32 error code for Win32 IO async calls (that want to throw).
		Private m_IntCompleted As Integer
		' Sign bit indicates synchronous completion if set.
		' Remaining bits count the number of InvokeCallbak() calls.
		Private m_EndCalled As Boolean
		' true if the user called the End*() method.
		Private m_UserEvent As Boolean
		' true if the event has been (or is about to be) handed to the user
		Private m_Event As Object
		' lazy allocated event to be returned in the IAsyncResult for the client to wait on

		Friend Sub New(myObject As Object, myState As Object, myCallBack As AsyncCallback)
			m_AsyncObject = myObject
			m_AsyncState = myState
			m_AsyncCallback = myCallBack
			m_Result = DBNull.Value

			GlobalLog.Print("LazyAsyncResult#" + ValidationHelper.HashString(Me) & "::.ctor()")
		End Sub

		' Allows creating a pre-completed result with less interlockeds.  Beware!  Constructor calls the callback.
		' if a derived class ever uses this and overloads Cleanup, this may need to change
		Friend Sub New(myObject As Object, myState As Object, myCallBack As AsyncCallback, result As Object)
			GlobalLog.Assert(result IsNot DBNull.Value, "LazyAsyncResult#{0}::.ctor()|Result can't be set to DBNull - it's a special internal value.", ValidationHelper.HashString(Me))
			m_AsyncObject = myObject
			m_AsyncState = myState
			m_AsyncCallback = myCallBack
			m_Result = result
			m_IntCompleted = 1

			If m_AsyncCallback IsNot Nothing Then
				GlobalLog.Print("LazyAsyncResult#" + ValidationHelper.HashString(Me) & "::Complete() invoking callback")
				m_AsyncCallback(Me)
			Else
				GlobalLog.Print("LazyAsyncResult#" + ValidationHelper.HashString(Me) & "::Complete() no callback to invoke")
			End If

			GlobalLog.Print("LazyAsyncResult#" + ValidationHelper.HashString(Me) & "::.ctor() (pre-completed)")
		End Sub

		' Interface method to return the original async object:
		Friend ReadOnly Property AsyncObject() As Object
			Get
				Return m_AsyncObject
			End Get
		End Property

		' Interface method to return the caller's state object.
		Public ReadOnly Property AsyncState() As Object Implements IAsyncResult.AsyncState
			Get
				Return m_AsyncState
			End Get
		End Property

		Protected Property AsyncCallback() As AsyncCallback
			Get
				Return m_AsyncCallback
			End Get

			Set
				m_AsyncCallback = value
			End Set
		End Property

		' Interface property to return a WaitHandle that can be waited on for I/O completion.
		' This property implements lazy event creation.
		' the event object is only created when this property is accessed,
		' since we're internally only using callbacks, as long as the user is using
		' callbacks as well we will not create an event at all.
		' If this is used, the event cannot be disposed because it is under the control of the
		' application.  Internal should use InternalWaitForCompletion instead - never AsyncWaitHandle.
		Public ReadOnly Property AsyncWaitHandle() As WaitHandle Implements IAsyncResult.AsyncWaitHandle
			Get
				GlobalLog.Print("LazyAsyncResult#" + ValidationHelper.HashString(Me) & "::get_AsyncWaitHandle()")

				#If DEBUG Then
				' Can't be called when state is protected.
				If _ProtectState Then
					Throw New InvalidOperationException("get_AsyncWaitHandle called in protected state")
				End If
				#End If

				Dim asyncEvent As ManualResetEvent

				' Indicates that the user has seen the event; it can't be disposed.
				m_UserEvent = True

				' The user has access to this object.  Lock-in CompletedSynchronously.
				If m_IntCompleted = 0 Then
					Interlocked.CompareExchange(m_IntCompleted, c_HighBit, 0)
				End If

				' Because InternalWaitForCompletion() tries to dispose this event, it's
				' possible for m_Event to become null immediately after being set, but only if
				' IsCompleted has become true.  Therefore it's possible for this property
				' to give different (set) events to different callers when IsCompleted is true.
				asyncEvent = DirectCast(m_Event, ManualResetEvent)
				While asyncEvent Is Nothing
					LazilyCreateEvent(asyncEvent)
				End While

				GlobalLog.Print(("LazyAsyncResult#" + ValidationHelper.HashString(Me) & "::get_AsyncWaitHandle() m_Event:") + ValidationHelper.HashString(m_Event))
				Return asyncEvent
			End Get
		End Property

		' Returns true if this call created the event.
		' May return with a null handle.  That means it thought it got one, but it was disposed in the mean time.
		Private Function LazilyCreateEvent(waitHandle As ManualResetEvent) As Boolean
			' lazy allocation of the event:
			' if this property is never accessed this object is never created
			waitHandle = New ManualResetEvent(False)
			Try
				If Interlocked.CompareExchange(m_Event, waitHandle, Nothing) Is Nothing Then
					If InternalPeekCompleted Then
						waitHandle.[Set]()
					End If
					Return True
				Else
					waitHandle.Close()
					waitHandle = DirectCast(m_Event, ManualResetEvent)
					' There's a chance here that m_Event became null.  But the only way is if another thread completed
					' in InternalWaitForCompletion and disposed it.  If we're in InternalWaitForCompletion, we now know
					' IsCompleted is set, so we can avoid the wait when waitHandle comes back null.  AsyncWaitHandle
					' will try again in this case.
					Return False
				End If
			Catch
				' This should be very rare, but doing this will reduce the chance of deadlock.
				m_Event = Nothing
				If waitHandle IsNot Nothing Then
					waitHandle.Close()
				End If
				Throw
			End Try
		End Function

		' This allows ContextAwareResult to not let anyone trigger the CompletedSynchronously tripwire while the context is being captured.
		<Conditional("DEBUG")> _
		Protected Sub DebugProtectState(protect As Boolean)
			#If DEBUG Then
			_ProtectState = protect
			#End If
		End Sub

		' Interface property, returning synchronous completion status.
		Public ReadOnly Property CompletedSynchronously() As Boolean Implements IAsyncResult.CompletedSynchronously
			Get
				GlobalLog.Print("LazyAsyncResult#" + ValidationHelper.HashString(Me) & "::get_CompletedSynchronously()")

				#If DEBUG Then
				' Can't be called when state is protected.
				If _ProtectState Then
					Throw New InvalidOperationException("get_CompletedSynchronously called in protected state")
				End If
				#End If

				' If this returns greater than zero, it means it was incremented by InvokeCallback before anyone ever saw it.
				Dim result As Integer = m_IntCompleted
				If result = 0 Then
					result = Interlocked.CompareExchange(m_IntCompleted, c_HighBit, 0)
				End If
				GlobalLog.Print("LazyAsyncResult#" + ValidationHelper.HashString(Me) & "::get_CompletedSynchronously() returns: " & (If((result > 0), "true", "false")))
				Return result > 0
			End Get
		End Property

		' Interface property, returning completion status.
		Public ReadOnly Property IsCompleted() As Boolean Implements IAsyncResult.IsCompleted
			Get
				GlobalLog.Print("LazyAsyncResult#" + ValidationHelper.HashString(Me) & "::get_IsCompleted()")

				#If DEBUG Then
				' Can't be called when state is protected.
				If _ProtectState Then
					Throw New InvalidOperationException("get_IsCompleted called in protected state")
				End If
				#End If

				' Look at just the low bits to see if it's been incremented.  If it hasn't, set the high bit
				' to show that it's been looked at.
				Dim result As Integer = m_IntCompleted
				If result = 0 Then
					result = Interlocked.CompareExchange(m_IntCompleted, c_HighBit, 0)
				End If
				Return (result And Not c_HighBit) <> 0
			End Get
		End Property

		' Use to see if something's completed without fixing CompletedSynchronously
		Friend ReadOnly Property InternalPeekCompleted() As Boolean
			Get
				Return (m_IntCompleted And Not c_HighBit) <> 0
			End Get
		End Property

		' Internal property for setting the IO result.
		Friend Property Result() As Object
			Get
				Return If(m_Result Is DBNull.Value, Nothing, m_Result)
			End Get
			Set
				' Ideally this should never be called, since setting
				' the result object really makes sense when the IO completes.
				'
				' But if the result was set here (as a preemptive error or for some other reason),
				' then the "result" parameter passed to InvokeCallback() will be ignored.
				'

				' It's an error to call after the result has been completed or with DBNull.
				GlobalLog.Assert(value IsNot DBNull.Value, "LazyAsyncResult#{0}::set_Result()|Result can't be set to DBNull - it's a special internal value.", ValidationHelper.HashString(Me))
				GlobalLog.Assert(Not InternalPeekCompleted, "LazyAsyncResult#{0}::set_Result()|Called on completed result.", ValidationHelper.HashString(Me))
				m_Result = value
			End Set
		End Property

		Friend Property EndCalled() As Boolean
			Get
				Return m_EndCalled
			End Get
			Set
				m_EndCalled = value
			End Set
		End Property

		' Internal property for setting the Win32 IO async error code.
		Friend Property ErrorCode() As Integer
			Get
				Return m_ErrorCode
			End Get
			Set
				m_ErrorCode = value
			End Set
		End Property

		' A method for completing the IO with a result
		' and invoking the user's callback.
		' Used by derived classes to pass context into an overridden Complete().  Useful
		' for determining the 'winning' thread in case several may simultaneously call
		' the equivalent of InvokeCallback().
		Protected Sub ProtectedInvokeCallback(result As Object, userToken As IntPtr)
			GlobalLog.Print("LazyAsyncResult#" + ValidationHelper.HashString(Me) & "::ProtectedInvokeCallback() result = " & (If(TypeOf result Is Exception, DirectCast(result, Exception).Message, If(result Is Nothing, "<null>", result.ToString()))) & ", userToken:" & userToken.ToString())

			' Critical to disallow DBNull here - it could result in a stuck spinlock in WaitForCompletion.
			If result Is DBNull.Value Then
				Throw New ArgumentNullException("result")
			End If

			#If DEBUG Then
			' Always safe to ask for the state now.
			_ProtectState = False
			#End If

			If (m_IntCompleted And Not c_HighBit) = 0 AndAlso (Interlocked.Increment(m_IntCompleted) And Not c_HighBit) = 1 Then
				' DBNull.Value is used to guarantee that the first caller wins,
				' even if the result was set to null.
				If m_Result Is DBNull.Value Then
					m_Result = result
				End If

				' Does this need a memory barrier to be sure this thread gets the m_Event if it's set?  I don't think so
				' because the Interlockeds on m_IntCompleted/m_Event should serve as the barrier.
				Dim asyncEvent As ManualResetEvent = DirectCast(m_Event, ManualResetEvent)
				If asyncEvent IsNot Nothing Then
					asyncEvent.[Set]()
				End If

				Complete(userToken)
			End If
		End Sub

		' A method for completing the IO with a result
		' and invoking the user's callback.
		Friend Sub InvokeCallback(result As Object)
			ProtectedInvokeCallback(result, IntPtr.Zero)
		End Sub

		' A method for completing the IO without a result
		' and invoking the user's callback.
		Friend Sub InvokeCallback()
			ProtectedInvokeCallback(Nothing, IntPtr.Zero)
		End Sub

		'
		'  MUST NOT BE CALLED DIRECTLY
		'  A protected method that does callback job and it is guaranteed to be called exactly once.
		'  A derived overriding method must call the base class somewhere or the completion is lost.
		'
		Protected Overridable Sub Complete(userToken As IntPtr)
			Dim offloaded As Boolean = False
			Dim threadContext As ThreadContext = CurrentThreadContext
			Try
				threadContext.m_NestedIOCount += 1
				If m_AsyncCallback IsNot Nothing Then
					GlobalLog.Print("LazyAsyncResult#" + ValidationHelper.HashString(Me) & "::Complete() invoking callback")

					If threadContext.m_NestedIOCount >= c_ForceAsyncCount Then
						GlobalLog.Print("LazyAsyncResult::Complete *** OFFLOADED the user callback ***")
						ThreadPool.QueueUserWorkItem(New WaitCallback(AddressOf WorkerThreadComplete))
						offloaded = True
					Else
						m_AsyncCallback(Me)
					End If
				Else
					GlobalLog.Print("LazyAsyncResult#" + ValidationHelper.HashString(Me) & "::Complete() no callback to invoke")
				End If
			Finally
				threadContext.m_NestedIOCount -= 1

				' Never call this method unless interlocked m_IntCompleted check has succeeded (like in this case)
				If Not offloaded Then
					Cleanup()
				End If
			End Try
		End Sub



		' Only called in the above method
		Private Sub WorkerThreadComplete(state As Object)
			Try
				m_AsyncCallback(Me)
			Finally
				Cleanup()
			End Try
		End Sub

		' Custom instance cleanup method.
		' Derived types override this method to release unmanaged resources associated with an IO request.
		Protected Overridable Sub Cleanup()
		End Sub

		Friend Function InternalWaitForCompletion() As Object
			Return WaitForCompletion(True)
		End Function

		'
'        internal object InternalWaitForCompletionNoSideEffects()
'        {
'            return WaitForCompletion(false);
'        }
'        


		Private Function WaitForCompletion(snap As Boolean) As Object
			Dim waitHandle As ManualResetEvent = Nothing
			Dim createdByMe As Boolean = False
			Dim complete As Boolean = If(snap, IsCompleted, InternalPeekCompleted)

			If Not complete Then
				' Not done yet, so wait:
				waitHandle = DirectCast(m_Event, ManualResetEvent)
				If waitHandle Is Nothing Then
					createdByMe = LazilyCreateEvent(waitHandle)
				End If
			End If

			If waitHandle IsNot Nothing Then
				Try
					GlobalLog.Print(("LazyAsyncResult#" + ValidationHelper.HashString(Me) & "::InternalWaitForCompletion() Waiting for completion m_Event#") + ValidationHelper.HashString(waitHandle))
					waitHandle.WaitOne(Timeout.Infinite, False)
						' This can occur if this method is called from two different threads.
						' This possibility is the trade-off for not locking.
				Catch generatedExceptionName As ObjectDisposedException
				Finally
					' We also want to dispose the event although we can't unless we did wait on it here.
					If createdByMe AndAlso Not m_UserEvent Then
						' Does m_UserEvent need to be volatile (or m_Event set via Interlocked) in order
						' to avoid giving a user a disposed event?
						Dim oldEvent As ManualResetEvent = DirectCast(m_Event, ManualResetEvent)
						m_Event = Nothing
						If Not m_UserEvent Then
							oldEvent.Close()
						End If
					End If
				End Try
			End If

			' A race condition exists because InvokeCallback sets m_IntCompleted before m_Result (so that m_Result
			' can benefit from the synchronization of m_IntCompleted).  That means you can get here before m_Result got
			' set (although rarely - once every eight hours of stress).  Handle that case with a spin-lock.
			While m_Result Is DBNull.Value
				Thread.SpinWait(1)
			End While

			GlobalLog.Print("LazyAsyncResult#" + ValidationHelper.HashString(Me) & "::InternalWaitForCompletion() done: " & (If(TypeOf m_Result Is Exception, DirectCast(m_Result, Exception).Message, If(m_Result Is Nothing, "<null>", m_Result.ToString()))))

			Return m_Result
		End Function

		' A general interface that is called to release unmanaged resources associated with the class.
		' It completes the result but doesn't do any of the notifications.
		Friend Sub InternalCleanup()
			If (m_IntCompleted And Not c_HighBit) = 0 AndAlso (Interlocked.Increment(m_IntCompleted) And Not c_HighBit) = 1 Then
				' Set no result so that just in case there are waiters, they don't hang in the spin lock.
				m_Result = Nothing
				Cleanup()
			End If
		End Sub
	End Class
End Namespace

Open in new window

0
 

Author Comment

by:mediasoftware
ID: 33467211
To all experts: Please note that LazyAsyncResult is not an recognized expression in VB.NET 2008 IDE.

Thank you in advance.
0
 
LVL 52

Expert Comment

by:Carl Tawn
ID: 33467296
The fact it's not recognised is nothing to do with it being VB. It's to do with the fact that you copied the code for the TcpListener class but not for the LazyAsyncResult class that it uses. The code posted by PhilAI should be what you need. Otherwise you can find the original code here:

    http://msdn.krugle.com/kse/entfiles/gdpe/codeplex.com/scmi_17301/fx/src/net/system/net/_lazyasyncresult.cs#2
0
 

Author Closing Comment

by:mediasoftware
ID: 33467610
Thank you very much PhilAI.
0

Featured Post

Maximize Your Threat Intelligence Reporting

Reporting is one of the most important and least talked about aspects of a world-class threat intelligence program. Here’s how to do it right.

Join & Write a Comment

Recently while returning home from work my wife (another .NET developer) was murmuring something. On further poking she said that she has been assigned a task where she has to serialize and deserialize objects and she is afraid of serialization. Wha…
In my previous two articles we discussed Binary Serialization (http://www.experts-exchange.com/A_4362.html) and XML Serialization (http://www.experts-exchange.com/A_4425.html). In this article we will try to know more about SOAP (Simple Object Acces…
Access reports are powerful and flexible. Learn how to create a query and then a grouped report using the wizard. Modify the report design after the wizard is done to make it look better. There will be another video to explain how to put the final p…
This video demonstrates how to create an example email signature rule for a department in a company using CodeTwo Exchange Rules. The signature will be inserted beneath users' latest emails in conversations and will be displayed in users' Sent Items…

707 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question

Need Help in Real-Time?

Connect with top rated Experts

14 Experts available now in Live!

Get 1:1 Help Now