11

I am using the answer in this topic. iPhone - how to determine carrier of the device (AT&T, Verizon, etc?) which is the same as getting operator details in iphone. Although it works fine when using a sim card, the returned carrier name if there is no SIM card is the old carrier name. It doesn't detect that the SIM is removed.

I know this contradicts with Apple documentation that if there is no carrier, CTCarrier object shall be nil. But in my app I logged the carrier info and it gives me the latest carrier name although no sim is installed.

Community
  • 1
  • 1
Abdalrahman Shatou
  • 4,550
  • 6
  • 50
  • 79

6 Answers6

12

According to the documentation for [CTCarrier carrierName]:

If you configure a device for a carrier and then remove the SIM card, this property retains the name of the carrier.

As far as I know, you cannot detect if the SIM card is installed. You can only determine if a WWAN connection is available using Reachability.

Evan Mulawski
  • 54,662
  • 15
  • 117
  • 144
  • 1
    This helped but didn't solve the problem. WWAN connection may not exist, but SIM card may be still inserted (if the user switches off the data and 3G). – Abdalrahman Shatou May 07 '12 at 23:00
  • 2
    Right, and there is no way to check if the SIM card is present. – Evan Mulawski May 07 '12 at 23:02
  • 2
    In the same documentation link you provided, can't `mobileCountryCode` or `mobileNetworkCode` be used to detect if SIM is present or not? The documentation states that those values will be `nil` if there is no SIM present. It doesn't seem that those properties are retained – wnafee Jun 17 '12 at 00:30
  • @wnafee Unfortunately, that is not always the case, as the values are retained unless the device is restarted after removing the SIM card. However, YMMV with different iOS versions. – Evan Mulawski Jun 17 '12 at 00:34
9
@import CoreTelephony;

-(BOOL)hasCellularCoverage
{
    CTTelephonyNetworkInfo *networkInfo = [CTTelephonyNetworkInfo new];
    CTCarrier *carrier = [networkInfo subscriberCellularProvider];


    if (!carrier.isoCountryCode) {
        NSLog(@"No sim present Or No cellular coverage or phone is on airplane mode.");
        return NO;
    }
    return YES;
}
muzz
  • 4,324
  • 2
  • 24
  • 14
8

The CTCarrier object has 5 properties:

allowsVOIP
carrierName
isoCountryCode
mobileCountryCode
mobileNetworkCode

I have made some tests regarding CTCarrier and I have come to the conclusion that for iOS 7 only carrierName and allowsVOIP are retained when SIM is removed. isoCountryCode, mobileCountryCode and mobileNetworkCode are reset for iOS 7. That's how you can detect if a SIM is present or not.

For iOS 6 all the values are retained.

I performed the tests using an iPhone 4S and iPhone 5 both running iOS 7.

vgru
  • 49,838
  • 16
  • 120
  • 201
4spins
  • 144
  • 2
  • 3
1

Swift version:

func hasCellularCoverage() -> Bool {

    let networkInfo = CTTelephonyNetworkInfo()

    guard let info = networkInfo.subscriberCellularProvider else {return false}

    if let carrier = info.isoCountryCode {
        print("No sim present Or No cellular coverage or phone is on airplane mode. Carrier = \(carrier)");
        return false
    }

    return true

}

or

func hasCellularCoverage() -> Bool {

    let networkInfo = CTTelephonyNetworkInfo()

    guard let info = networkInfo.subscriberCellularProvider else {return false}

    return info.isoCountryCode != nil ? false : true

}
L33MUR
  • 4,002
  • 2
  • 12
  • 27
1

hope this helps:

    if #available(iOS 12.0, *) {
        return CTTelephonyNetworkInfo().serviceSubscriberCellularProviders?.first?.value.mobileNetworkCode != nil
    } else {
        if let _ = CTTelephonyNetworkInfo().subscriberCellularProvider?.isoCountryCode {
            return true
        } else {
            return false
        }
    }
horn
  • 11
  • 1
0

Swift 5.4 answer

Accepted answer is outdated or incorrect.

protocol SimCardServiceProtocol {
    var isAvailableSIM: Bool { get }
}

final class SimCardService: SimCardServiceProtocol {

    var isAvailableSIM: Bool {
        return CTTelephonyNetworkInfo().serviceSubscriberCellularProviders?.first?.value.mobileNetworkCode != nil
    }
}
swift2geek
  • 1,697
  • 1
  • 20
  • 27