I have a client application that needs to access to its server though VPN. If the .NET Remoting call passes serializable objects between server and client, everything works. However, the client app also make a remoting call that passes a MarshalByRefObject argument, this failed because the underlying TCP connection failed to make the connection back to client's.
Unfortunately I don't have control over the corporate VPN setup, and I am not familiar with how VPN works. I tested with all firewall off, but somehow the cooperate VPN network would not allow internal network connect to the external network (client machine). I guess it of make sense to block internal network connect to an external source for security reason. The VPN client in question is Cisco AnyConnect Secure Mobile Client.
My questions are:
Is this a limitation in .NET remoting when using MarshalByRefObject?
If I switch to WCF, would .NET TCP Binding Duplex connection work?
If I can recommend something to the IT department, what should I tell them to configure their VPN (if possible)?
What would be the recommended practice when writing a client-server applications though VPN?
Here is a stack trace when .NET remoting trying to marshal back to the client by failed:
Note: 10.8.26.34 is my client IP Address, and 8080 is the registered for .NET Remoting TCP channel. The ME.Streets.Service.Interface.LoadScheduleHelper is the class that derived from MarshalByRefObject, which has a property call ScheduleKey that need to be marshal to the client for the data.
Exception
System.Net.Sockets.SocketException (0x80004005): A connection attempt failed because the connected party did not properly respond after a period of time, or established connection failed because connected host has failed to respond 10.8.26.34:8080
Server stack trace:
at System.Net.Sockets.Socket.DoConnect(EndPoint endPointSnapshot, SocketAddress socketAddress)
at System.Net.Sockets.Socket.Connect(EndPoint remoteEP)
at System.Runtime.Remoting.Channels.RemoteConnection.CreateNewSocket(EndPoint ipEndPoint)
at System.Runtime.Remoting.Channels.RemoteConnection.CreateNewSocket()
at System.Runtime.Remoting.Channels.SocketCache.GetSocket(String machinePortAndSid, Boolean openNew)
at System.Runtime.Remoting.Channels.Tcp.TcpClientTransportSink.SendRequestWithRetry(IMessage msg, ITransportHeaders requestHeaders, Stream requestStream)
at System.Runtime.Remoting.Channels.Tcp.TcpClientTransportSink.ProcessMessage(IMessage msg, ITransportHeaders requestHeaders, Stream requestStream, ITransportHeaders& responseHeaders, Stream& responseStream)
at System.Runtime.Remoting.Channels.BinaryClientFormatterSink.SyncProcessMessage(IMessage msg)
Exception rethrown
at [0]:
at System.Runtime.Remoting.Proxies.RealProxy.HandleReturnMessage(IMessage reqMsg, IMessage retMsg)
at System.Runtime.Remoting.Proxies.RealProxy.PrivateInvoke(MessageData& msgData, Int32 type)
at ME.Streets.Service.Interface.LoadScheduleHelper.get_ScheduleKey()
at ME.Streets.Service.Provider.Remoting.ServiceEndPoints.ServiceEndPoint.LoadScheduleByPrimaryKeyInChunkWorker(LoadScheduleHelper loadScheduleHelper, Boolean loadFromDev) in c:\dev\Streets\Main\Streets\ME.Streets.Service.Provider\Remoting\ServiceEndPoints\ServiceEndPoint.sch_Schedule.cs:line 634
...
Related
I am writing an Azure Function to ping a particular host to check response times using the System.Net.NetworkInformation.Ping class. I get a generic exception when calling Ping.Send, however this works fine locally.
Are there restrictions on network calls made outbound from Azure Functions?
The exception I get is simply:
Could not ping: An exception occurred during a Ping request.
at System.Net.NetworkInformation.Ping.Send(IPAddress address, Int32 timeout, Byte[] buffer, PingOptions options)
at System.Net.NetworkInformation.Ping.Send(String hostNameOrAddress, Int32 timeout, Byte[] buffer, PingOptions options
As ICMP protocol is not permitted through the Azure, you will not be able to ping an Azure VM from the internet, and from within the Azure VM, you are unable to ping internet locations.
To test connectivity, it is recommended to do a port ping. While Ping.exe uses ICMP, other tools such as PsPing, Nmap, or Telnet which allows you to test connectivity to a specific TCP port.
It is nicely explained in this post - https://blogs.msdn.microsoft.com/mast/2014/06/22/use-port-pings-instead-of-icmp-to-test-azure-vm-connectivity/
Consider the situation where some client calls WebMethod and after connection was established the host process crashes and connection becomes half-open. Will ASP.NET WebMethod proxy automatically detect it?
We assume that WebMethod timeout settled to the infinity or some big amount of time. Will connectivity error be detected only on TCP keep-alive packet sending (after 2 hours of idle on Windows by default)?
[WebService(Namespace = "http://www.example.com/TestService/")]
[WebServiceBinding(ConformsTo = WsiProfiles.BasicProfile1_1)]
public class TestService : System.Web.Services.WebService
{
[WebMethod]
public void DoLongWork()
{
// long work here
}
}
Web Reference proxy call:
public void ServiceClient()
{
var serviceProxy = new MyNamespace.TestService();
// serviceProxy.Url = ...
serviceProxy.Timeout = -1; // do not use timeout
// will it wait for 2 hours (when TCP keep-alive will be sent) if connection was lost after handshake?
serviceProxy.DoLongWork();
}
UPDATE.
I've tried multiple scenarios and here the results that I got using Wireshark to see what is going on under the hood.
Stopping hosting Web Server (IIS) through the IIS Manager or killing host process (w3wp.exe):
In both cases client notified via sending TCP RST flag. Seems Windows takes care of closing sockets for crashed/killed processes. In .NET the System.Net.WebException will be thrown:
Unhandled Exception: System.Net.WebException: The underlying connection was closed: An unexpected error occurred on a receive. ---> System.IO.IOException: Unable to read data from the transport connection: An existing connection was forcibly closed by the remote host. ---> System.Net.Sockets.SocketException: An existing connection was forcibly closed by the remote host
at System.Net.Sockets.Socket.Receive(Byte[] buffer, Int32 offset, Int32 size, SocketFlags socketFlags)
at System.Net.Sockets.NetworkStream.Read(Byte[] buffer, Int32 offset, Int32 size)
--- End of inner exception stack trace ---
at System.Net.Sockets.NetworkStream.Read(Byte[] buffer, Int32 offset, Int32 size)
at System.Net.PooledStream.Read(Byte[] buffer, Int32 offset, Int32 size)
at System.Net.Connection.SyncRead(HttpWebRequest request, Boolean userRetrievedStream, Boolean probeRead)
--- End of inner exception stack trace ---
at System.Web.Services.Protocols.WebClientProtocol.GetWebResponse(WebRequest request)
at System.Web.Services.Protocols.HttpWebClientProtocol.GetWebResponse(WebRequest request)
at System.Web.Services.Protocols.SoapHttpClientProtocol.Invoke(String methodName, Object[] parameters)
at WebMethodAndTCPHalfOpenTest.TestWebReference.TestService.DoLongWork(Int32 sec)
at WebMethodAndTCPHalfOpenTest.Program.Main(String[] args)
Killed the host process after connectivity (to the host) loss, so TCP RST can not reach client:
Results here is very tangling for me, because after 2.5 hours the broken connection (half-open) is not detected and client still thinks that underlying TCP connection is alive (the same situation after 6 hours). Here the output from Sysinternals TCPView:
TCPView v3.01 - TCP/UDP endpoint viewer Copyright (C) 1998-2010
Mark Russinovich and Bryce Cogswell Sysinternals -
www.sysinternals.com
[TCP] WebMethodAndTCPHalfOpenTest.exe
PID: 8180
State: ESTABLISHED
Local: 192.168.1.2
Remote: 5.167.159.81
Windows Version: Microsoft Windows [Version 6.1.7601]
Wireshark output:
I've checked KeepAliveTime registry setting on my system here: HKLM\SYSTEM\CurrentControlSet\Services\Tcpip\Parameters and it was missing, so the default 2 hours should be used (?).
Can anybody explain the result described in the second point? Why TCP keepalive was not sent? Is proxy explicitly settled up different keepalive behavior for underlying socket (https://msdn.microsoft.com/en-us/library/windows/desktop/ee470551(v=vs.85).aspx)?
It looks like the keep alive is not garanteed because things might muck with that setting in windows (no the registry value isn't the end all).
According to this:
Windows TCP socket has SO_KEEPALIVE enabled by default?
It looks like you should not rely on this behavior and set a timeout. If you are using a soap request, you could always invoke an async request, and then wait on the request based on a client configurable value, and have a nice logic handling for timeouts.
If the host process crashes the connection will close. It won't wait for the TCP keep-alive to kick. You can easily test this scenario by spinning your WebService and making it crash voluntary.
I have a windows service using C#(windows application) which performs a set of various functions.
But recently it was required to use a wsdl service (a url was provided) whose functions I have to use in my code.
Although I have never done it before but if I am not wrong we add the service reference creates its instance and then call its function.
I have done all these successfully.
But when i execute the service I get end point not found exception something like as below..
System.ServiceModel.EndpointNotFoundException: Could not connect to http://localhost:8082/quali-jaxrpc/quali. TCP error code 10061: No connection could be made because the target machine actively refused it 127.0.0.1:8082. ---> System.Net.WebException: Unable to connect to the remote server ---> System.Net.Sockets.SocketException: No connection could be made because the target machine actively refused it 127.0.0.1:8082
at System.Net.Sockets.Socket.DoConnect(EndPoint endPointSnapshot, SocketAddress socketAddress)
at System.Net.ServicePoint.ConnectSocketInternal(Boolean connectFailure, Socket s4, Socket s6, Socket& socket, IPAddress& address, ConnectSocketState state, IAsyncResult asyncResult, Int32 timeout, Exception& exception)
--- End of inner exception stack trace ---
at System.Net.HttpWebRequest.GetRequestStream(TransportContext& context)
at System.Net.HttpWebRequest.GetRequestStream()
at System.ServiceModel.Channels.HttpOutput.WebRequestHttpOutput.GetOutputStream()
--- End of inner exception stack trace ---
The problem is that the service is already running on the server itself but yet it is giving this exception..
Am I doing something wrong?
Please note that my service is not WCF its windows service.
When I added the service reference of the WSDL in appconfig following was created-
<endpoint address="http://localhost:8082/qualicision-jaxrpc/qualicision"
So i just replaced the localhost with the IP of the server.
Although the service is deployed on the server and windows service also running on same but still adding actual IP of the server in place of localhost worked.
I'm developing a windows service, that downloads images from a specific URL. The service runs correctly on my computer but when I install it in the server it does not download the image and it gives the following error:
System.Net.WebException: Unable to connect to the remote server --->
System.Net.Sockets.SocketException: A connection attempt failed because the connected party did not properly respond after a period of time, or established connection failed because connected host has failed to respond 212.100.220.117:80
at System.Net.Sockets.Socket.DoConnect(EndPoint endPointSnapshot, SocketAddress socketAddress)
at System.Net.ServicePoint.ConnectSocketInternal(Boolean connectFailure, Socket s4, Socket s6, Socket& socket, IPAddress& address, ConnectSocketState state, IAsyncResult asyncResult, Int32 timeout, Exception& exception)
--- End of inner exception stack trace ---
at System.Net.WebClient.DownloadDataInternal(Uri address, WebRequest& request)
at System.Net.WebClient.DownloadData(Uri address)
at System.Net.WebClient.DownloadData(String address)
What might be causing the error and how can I resolve it?
I read this page:
http://support.microsoft.com/kb/318140
I'm not sure if this is the problem, and if it is what proxy should I write in the config. Asking you for your advice.
I found the answer. I was trying to access the public address "http://mywebsite.com/images/" from the server. Instead of that I used the local IP of the server hosted the website and it's now working.
In this case it might be possible that port 80 is not open. Create an inbound and outbound rule in firewall setting to open port 80. Still, if the issue exists try with disabling the antivirus, It might be possible that antivirus is blocking the port.
In my case I had to modify the Logon settings of the Windows Service in the Windows Service console then used domain administrator account to run the service instead of the regular Local System/Service account then It started working properly.
If you are working, this could indicate that you aren't connected to your VPN.
I am sending an email from a WPF application. When sending as a domain user on the network, the emails sends as expected. However, when I attempt to send email over a VPN connection, I get the following exception:
Exception:
System.Net.Mail.SmtpException: Failure sending mail. ---> System.IO.IOException: Unable to read data from the transport connection: net_io_connectionclosed.
at System.Net.Mail.SmtpReplyReaderFactory.ProcessRead(Byte[] buffer, Int32 offset, Int32 read, Boolean readLine)
at System.Net.Mail.SmtpReplyReaderFactory.ReadLines(SmtpReplyReader caller, Boolean oneLine)
at System.Net.Mail.SmtpReplyReaderFactory.ReadLine(SmtpReplyReader caller)
at System.Net.Mail.SmtpConnection.GetConnection(String host, Int32 port)
at System.Net.Mail.SmtpTransport.GetConnection(String host, Int32 port)
at System.Net.Mail.SmtpClient.GetConnection()
at System.Net.Mail.SmtpClient.Send(MailMessage message)
I have tried using impersonation as well as setting the Credentials on the SmtpClient. Neither seem to work:
using (new ImpersonateUser("myUser", "MYDOMAIN", "myPass"))
{
var client = new SmtpClient("myhost.com");
client.UseDefaultCredentials = true;
client.Credentials = new NetworkCredential("myUser", "myPass", "MYDOMAIN");
client.Send(mailMessage);
}
I've also tried using Wireshark to view the message over the wire, but I don't know enough about SMTP to know what I'm looking for.
One other variable is that the machine I'm using on the VPN is Vista Business and the machine on the network is Win7. I don't think it's related, but then I wouldn't be asking if I knew the issue! :)
Any ideas?
I solved this by connecting outlook on a VPN machine to the Exchange server. The IP address automatically resolved to a different server name than the one I was trying. Evidently the exchange server was only available over VPN through the other URL.