I am working on an app that requires access to a resource behind a VPN.
We have on-demand VPN setup using Cisco AnyConnect but we keep running into an issue that in the middle of using the app, the VPN will close.
Sometimes the user will try to log-in, the vpn will establish, user will be logged in, then the VPN will immediately drop.
Is there something I can (or should) do to the NSURLSession that will keep it alive?
I checked my request headers and I have "connection: keep-alive set", but the server is responding "connection: close" is this correct?
Those are two entirely orthogonal things. Keep-alive tells the server that your app is willing to reuse the TCP connection to make multiple HTTP requests instead of creating a separate connection for each request. It has nothing to do with the VPN connection. And the server on the other end is free to refuse keep-alive requests if it doesn't support them (or is configured to refuse them). So that's perfectly reasonable.
The VPN connection dropping is probably caused either by hitting a URL that has been specifically configured to cause the VPN to disconnect or by the VPN crashing, but it could also be caused by too short a timeout in the VPN configuration.
Either way, it is a problem with the VPN or its configuration, and I doubt there's anything you can do about it as the author of an app that is just trying to send data through it. Probably the best you can do is to use reachability to determine whether a request will cause the VPN to connect, and make a note to more aggressively retry requests that fail if you see that flag....
Usually Random disconnection problem in VPNs, is about bad MTU settings on your interfaces. I wrote a complete answer here about how to set MTU in linux, for vpn.
You usually have to has a 1400 MTU for your internet connection interface, and 1300 MTU for your VPN connection.
I don't know how to set it in IOS, but at least you can check your MTU settings to be sure if it's about MTU or not, if you had MTU 1500 then it means your VPN is disconnecting because of it.
Related
I'd like to find out if a Wi-Fi has internet connection or not. Sometimes our devices are connected with Wi-Fi, but the Wi-Fi doesn't have an internet connection.
NWPathMonitor or Connectivity thirdparty. I tried it, but it is not fool proof.
I know I can write a method to ping a server, but this is a very ineffective and costly affair.
Any ideas?
The only way to know for sure if a network has an Internet connection is to try and make a connection to the Internet. There is nothing on the device that you can query to get the answer.
Even if there were it would have to resort to polling/pinging since connectivity can change at any instant.
A WiFi connection can transition from no-Internet to Internet when the user completes a Hotspot login form. A WiFi connection can transition from Internet to no-Internet if the upstream Internet connection fails in some way. A WiFi connection may be connected to the Internet but not be able to communicate with the specific host your app needs due to a routing failure or some other issue.
For all of these reasons Apple actively discourages "pre flight" checks. Even if a check passes a network operation can still fail due to a change in network status that occurred a microsecond later. It is also unnecessary overhead as it is generally a safe assumption that most devices have some sort of Internet connection most of the time, particularly if the device is an iPhone.
You need to handle errors anyway. Just try the operation and see what happens. If there is no network connection it will fail pretty quickly.
If you want to provide more feedback to the user then you could begin actively checking Internet connectivity with exponential back off in response to a connection error.
That way your app isn't constantly "pinging".
You can also use the error to start a process that uses SCNetworkReachability to check connectivity for you. Rather than using that framework directly, particularly if you are writing in Swift, you might like to use something that wraps it and makes it more accessible like Ashley Mills' Reachability.swift
I am tunnelling my traffic through a server. In some cases it has to block determinate websites, e.g. gambling sites. The tunnel works without a problem if I start the tunnel with WiFi or Cellular. When I change the network to the opposite the VPN reconnects automatically as I am using on demand VPN but the VPN doesn't block the websites it did before. My main supposition is that after changing the interface, WiFi to Cellular or vice versa, the outgoing traffic from the device it is not routed through the tunnel interface (utun) but the VPN is still up.
How could I check or "force" the outgoing traffic through my tunnel interface?
I can detect when the interface changes and I could force restart the tunnel but I shouldn't do it. That should be the tunnel's task and I prefer not to force the tunnel's state.
As I see in Session 717 from 2015 WWDC the VPN connnection is stablished and then goes down level by level in the Internet stack until the interface level. When the VPN has been stablished it uses the utun0 interface. My fear is when I stablish, for example, a tunnel using Wi-Fi connection it correctly routes the traffic out using the utun0 interface but when I change to the Cellular connection it uses another interface therefore my tunnel is still up but it doesn't apply the content blocking because the packets are not routed using the utun0 interface.
[EDIT] I've just discovered defaultPath​. Using KVO I am able to monitor interface changes. When I detect a interface change I try to reconnect the tunnel. In some cases I am able to solve the issues I had before and the blocking is applied but in other cases it does not. I'm trying to monitor the cases in which the interface changes and if the connection is established but I cannot wrap my head around all the possible cases.
I'm building an application that will run in a museum with a local area wifi network without internet access, for some strange reason I'm not able to fully "join" this network with an iOS device. Enabling internet access on this network solves the problem...
The network should provide only a web server and a DNS server, the access point has a DHCP server, android devices can connect to the network without problems.
When I try to join the network with the device it remains in a "spinning wheel" status, the DHCP server log on the debian server says it has assigned an address to the iOS device, and if I check for the wifi address with an application (like iSys o SBSettings) I see the WIFI DHCP assigned address.
But when my app (or safari) tries to connect to the web server the request is routed through the 3G connection and not completed.
In my app I'm using the standard "Reachability" framework from Apple to check the reachability of a provided host name through the wifi connection and I get 0 on the SCNetworkReachabilityFlags mask....
I'm quite sure the problem is due to the fact iOS (5.1 in my case) tries to check the reachability for some "standard" host in the network, before routing traffic through the WIFI connection.
Anyone knows what an iOS device do to "validate" a WIFI network? I can add hostnames or simple dummy services to the server machine if this can help me connect the device to a LOCAL-only network :)
It seems that iOS doesn't like to join networks without a gateway, also if the network is local you have to setup a correct gateway address.
Setting the gateway as the server itself did the trick and the device started to route TCP/IP over my local area wifi network.
Device is 8900 OS version 4.6.1
Getting this exception/message
The application atempted to open a connection to a location inside the firewall and outside the firewall which is not allowed by your security policy
when trying to open an http connection when firewall is on (allowed HTTP connections for the app when prompted). Exact same code works fine on other devices with firewall on.
any ideas?
The firewall in this case is actually the BES firewall - what you're encountering is known as the "split-pipe" scenario where the device is detecting that connections are being made both inside the firewall (via MDS) and outside the firewall (via Wi-Fi, Direct TCP, etc.) There are IT policies that can be enabled by the BES administrator to prevent "split-pipes" from happening. Here's a good forum post with more information:
http://supportforums.blackberry.com/t5/Java-Development/Connecting-your-BlackBerry-http-and-socket-connections-to-the/m-p/206252#M29108
I am doing an InternetConnect (Wininet) to an FTP server that happens to be running on an iPhone. When the user is on a normal WiFi network it works fine for him. When he has an ad hoc network with his iPhone he gets an ERROR_INTERNET_TIMEOUT. I presume this is some kind of routing problem. I am curious as to why this gets ERROR_INTERNET_TIMEOUT and not ERROR_INTERNET_CANNOT_CONNECT. Most users, if they are blocked by, for example, a firewall, will get ERROR_INTERNET_CANNOT_CONNECT.
I don't understand enough about low-level TCP/IP to understand what kind of situation would cause a timeout error instead of a connect error. I'm really more intellectually curious in understanding this than I am in actually solving the user's problem. ;-) Can anyone explain what is happening with the network packets (the more detailed the better)?
edit:
note that, as far as I know, the user doesn't have an outgoing firewall enabled, it's not a firewall issue. I think it's some kind of routing issue. I have seen similar issues when a user is connected a VPN and their routing is set up incorrectly and all packets go to their work instead of the iPhone. I want to know what's going on with the packets in this situation: the socket connects but at the next step (whatever that is) they can't communicate.
Firewalls these days choose to not respond at all to packets that they deem suspicious, this is to prevent port scanners from detecting that there is a machine at the IP. So that could be what is happening in your case, the firewall may simply be dropping the packet and causing a timeout rather than a failure to connect error.