How to unlock SIM card from command line in Ubuntu

Equipment and specifications:

I will use command mmcli to do everything. Important: I have anonymized some information with x characters for privacy reasons. Here is the process to follow:

  1. List available modems:
khadas@Khadas:~$ mmcli -L
    /org/freedesktop/ModemManager1/Modem/1 [Quectel] EM06-E
  1. In this case the modem number is 1. Now I am displaying the information about that modem specifically by running:
khadas@Khadas:~$ mmcli -m 1
  -----------------------------------
  General  |                    path: /org/freedesktop/ModemManager1/Modem/1
           |               device id: 9xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx7
  -----------------------------------
  Hardware |            manufacturer: Quectel
           |                   model: EM06-E
           |       firmware revision: EM06ELAR04A04M4G
           |          carrier config: ROW_Generic_3GPP
           | carrier config revision: 05219800
           |            h/w revision: EM06-E
           |               supported: gsm-umts, lte
           |                 current: gsm-umts, lte
           |            equipment id: 6xxxxxxxxxxxxx8
  -----------------------------------
  System   |                  device: /sys/devices/platform/soc/fde00000.crg3drd/xhci-hcd.0.auto/usb1/1-1/1-1.3
           |                 drivers: cdc_mbim, option
           |                  plugin: quectel
           |            primary port: cdc-wdm0
           |                   ports: cdc-wdm0 (mbim), ttyUSB0 (qcdm), ttyUSB1 (gps), 
           |                          ttyUSB2 (at), ttyUSB3 (at), wwan0 (net)
  -----------------------------------
  Status   |                    lock: sim-pin
           |          unlock retries: sim-pin (3)
           |                   state: locked
           |             power state: on
  -----------------------------------
  Modes    |               supported: allowed: 3g; preferred: none
           |                          allowed: 4g; preferred: none
           |                          allowed: 3g, 4g; preferred: 4g
           |                          allowed: 3g, 4g; preferred: 3g
           |                 current: allowed: 3g, 4g; preferred: 4g
  -----------------------------------
  Bands    |               supported: utran-1, utran-3, utran-5, utran-8, eutran-1, eutran-3, 
           |                          eutran-5, eutran-7, eutran-8, eutran-20, eutran-28, eutran-32, 
           |                          eutran-38, eutran-40, eutran-41
           |                 current: utran-1, utran-3, utran-5, utran-8, eutran-1, eutran-3, 
           |                          eutran-5, eutran-7, eutran-8, eutran-20, eutran-28, eutran-32, 
           |                          eutran-38, eutran-40, eutran-41
  -----------------------------------
  IP       |               supported: ipv4, ipv6, ipv4v6
  -----------------------------------
  3GPP     |           enabled locks: sim, fixed-dialing
  -----------------------------------
  SIM      |        primary sim path: /org/freedesktop/ModemManager1/SIM/0
           |          sim slot paths: slot 1: /org/freedesktop/ModemManager1/SIM/0 (active)
           |                          slot 2: none
  1. From the output we can see that the SIM card number is 0 and is currently active but locked. To unlock it I will use sudo to run:
khadas@Khadas:~$ sudo mmcli -i 0 --pin=0338
successfully sent PIN code to the SIM
  1. I will display the modem information again to confirm that the SIM card is now unlocked:
khadas@Khadas:~$ mmcli -m 1
  -----------------------------------
  General  |                    path: /org/freedesktop/ModemManager1/Modem/1
           |               device id: 9xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx7
  -----------------------------------
  Hardware |            manufacturer: Quectel
           |                   model: EM06-E
           |       firmware revision: EM06ELAR04A04M4G
           |          carrier config: ROW_Generic_3GPP
           | carrier config revision: 05219800
           |            h/w revision: EM06-E
           |               supported: gsm-umts, lte
           |                 current: gsm-umts, lte
           |            equipment id: 6xxxxxxxxxxxxx8
  -----------------------------------
  System   |                  device: /sys/devices/platform/soc/fde00000.crg3drd/xhci-hcd.0.auto/usb1/1-1/1-1.3
           |                 drivers: cdc_mbim, option
           |                  plugin: quectel
           |            primary port: cdc-wdm0
           |                   ports: cdc-wdm0 (mbim), ttyUSB0 (qcdm), ttyUSB1 (gps), 
           |                          ttyUSB2 (at), ttyUSB3 (at), wwan0 (net)
  -----------------------------------
  Numbers  |                     own: +xxxxxxxxxxx
  -----------------------------------
  Status   |                    lock: sim-pin2
           |          unlock retries: sim-pin (3), sim-pin2 (3)
           |                   state: registered
           |             power state: on
           |             access tech: lte
           |          signal quality: 16% (recent)
  -----------------------------------
  Modes    |               supported: allowed: 3g; preferred: none
           |                          allowed: 4g; preferred: none
           |                          allowed: 3g, 4g; preferred: 4g
           |                          allowed: 3g, 4g; preferred: 3g
           |                 current: allowed: 3g, 4g; preferred: 4g
  -----------------------------------
  Bands    |               supported: utran-1, utran-3, utran-5, utran-8, eutran-1, eutran-3, 
           |                          eutran-5, eutran-7, eutran-8, eutran-20, eutran-28, eutran-32, 
           |                          eutran-38, eutran-40, eutran-41
           |                 current: utran-1, utran-3, utran-5, utran-8, eutran-1, eutran-3, 
           |                          eutran-5, eutran-7, eutran-8, eutran-20, eutran-28, eutran-32, 
           |                          eutran-38, eutran-40, eutran-41
  -----------------------------------
  IP       |               supported: ipv4, ipv6, ipv4v6
  -----------------------------------
  3GPP     |                    imei: 2xxxxxxxxxxxxx9
           |           enabled locks: sim, fixed-dialing
           |             operator id: 39555
           |           operator name: Free
           |            registration: home
           |    packet service state: attached
  -----------------------------------
  3GPP EPS |    ue mode of operation: csps-2
           |     initial bearer path: /org/freedesktop/ModemManager1/Bearer/0
           |  initial bearer ip type: ipv4v6
  -----------------------------------
  SIM      |        primary sim path: /org/freedesktop/ModemManager1/SIM/0
           |          sim slot paths: slot 1: /org/freedesktop/ModemManager1/SIM/0 (active)
           |                          slot 2: none

SIM status registered means that I was able to unlock the SIM card and it suceesfully registered to a cellular tower.


After unlocking the SIM card, the next thing to do is to activate Mobile Data to connect get Internet access. Here's how to do it:

  1. See the status of the devices to identify the one of type gsm:
khadas@Khadas:~$ nmcli device status
DEVICE         TYPE      STATE         CONNECTION         
eth0           ethernet  connected     Wired connection 1 
cdc-wdm0       gsm       disconnected  --                 
wlan0          wifi      disconnected  --                 
wlan1          wifi      disconnected  --                 
dummy0         dummy     unmanaged     --                 
lo             loopback  unmanaged     --                 
p2p-dev-wlan0  wifi-p2p  unmanaged     --                 
p2p-dev-wlan1  wifi-p2p  unmanaged     --   
  1. Create a connection profile and do any necessary modifications to it. In my case I modified certain parameters that I saw Free sets by default after connecting via GUI to the Mobile Network in Ubuntu. Those parameters are provided by each Mobile Network Operator and change from one another. Here is the command sequence:
khadas@Khadas:~$ sudo nmcli connection edit type gsm con-name "Free SIM Card CLI"

===| nmcli interactive connection editor |===

Adding a new 'gsm' connection

Type 'help' or '?' for available commands.
Type 'print' to show all the connection properties.
Type 'describe [<setting>.<prop>]' for detailed property description.

You may edit the following settings: connection, gsm, serial, ppp, match, ipv4, ipv6, hostname, tc, proxy
nmcli> set gsm.username free
nmcli> set gsm.password free
nmcli> set gsm.apn free
nmcli> 
nmcli> print
===============================================================================
                Connection profile details (Free SIM Card CLI)
===============================================================================
connection.id:                          Free SIM Card CLI
connection.uuid:                        f59b8ee1-de54-48c6-837c-8001a555ccfa
connection.stable-id:                   --
connection.type:                        gsm
connection.interface-name:              --
connection.autoconnect:                 yes
connection.autoconnect-priority:        0
connection.autoconnect-retries:         -1 (default)
connection.multi-connect:               0 (default)
connection.auth-retries:                -1
connection.timestamp:                   0
connection.read-only:                   no
connection.permissions:                 --
connection.zone:                        --
connection.master:                      --
connection.slave-type:                  --
connection.autoconnect-slaves:          -1 (default)
connection.secondaries:                 --
connection.gateway-ping-timeout:        0
connection.metered:                     unknown
connection.lldp:                        default
connection.mdns:                        -1 (default)
connection.llmnr:                       -1 (default)
connection.dns-over-tls:                -1 (default)
connection.wait-device-timeout:         -1
-------------------------------------------------------------------------------
ipv4.method:                            auto
ipv4.dns:                               --
ipv4.dns-search:                        --
ipv4.dns-options:                       --
ipv4.dns-priority:                      0
ipv4.addresses:                         --
ipv4.gateway:                           --
ipv4.routes:                            --
ipv4.route-metric:                      -1
ipv4.route-table:                       0 (unspec)
ipv4.routing-rules:                     --
ipv4.ignore-auto-routes:                no
ipv4.ignore-auto-dns:                   no
ipv4.dhcp-client-id:                    --
ipv4.dhcp-iaid:                         --
ipv4.dhcp-timeout:                      0 (default)
ipv4.dhcp-send-hostname:                yes
ipv4.dhcp-hostname:                     --
ipv4.dhcp-fqdn:                         --
ipv4.dhcp-hostname-flags:               0x0 (none)
ipv4.never-default:                     no
ipv4.may-fail:                          yes
ipv4.required-timeout:                  -1 (default)
ipv4.dad-timeout:                       -1 (default)
ipv4.dhcp-vendor-class-identifier:      --
ipv4.dhcp-reject-servers:               --
-------------------------------------------------------------------------------
ipv6.method:                            auto
ipv6.dns:                               --
ipv6.dns-search:                        --
ipv6.dns-options:                       --
ipv6.dns-priority:                      0
ipv6.addresses:                         --
ipv6.gateway:                           --
ipv6.routes:                            --
ipv6.route-metric:                      -1
ipv6.route-table:                       0 (unspec)
ipv6.routing-rules:                     --
ipv6.ignore-auto-routes:                no
ipv6.ignore-auto-dns:                   no
ipv6.never-default:                     no
ipv6.may-fail:                          yes
ipv6.required-timeout:                  -1 (default)
ipv6.ip6-privacy:                       -1 (unknown)
ipv6.addr-gen-mode:                     stable-privacy
ipv6.ra-timeout:                        0 (default)
ipv6.dhcp-duid:                         --
ipv6.dhcp-iaid:                         --
ipv6.dhcp-timeout:                      0 (default)
ipv6.dhcp-send-hostname:                yes
ipv6.dhcp-hostname:                     --
ipv6.dhcp-hostname-flags:               0x0 (none)
ipv6.token:                             --
-------------------------------------------------------------------------------
gsm.auto-config:                        no
gsm.number:                             --
gsm.username:                           free
gsm.password:                           <hidden>
gsm.password-flags:                     0 (none)
gsm.apn:                                "free"
gsm.network-id:                         --
gsm.pin:                                <hidden>
gsm.pin-flags:                          0 (none)
gsm.home-only:                          no
gsm.device-id:                          --
gsm.sim-id:                             --
gsm.sim-operator-id:                    --
gsm.mtu:                                auto
-------------------------------------------------------------------------------
proxy.method:                           none
proxy.browser-only:                     no
proxy.pac-url:                          --
proxy.pac-script:                       --
-------------------------------------------------------------------------------
nmcli> save
Saving the connection with 'autoconnect=yes'. That might result in an immediate activation of the connection.
Do you still want to save? (yes/no) [yes] yes
Connection 'Free SIM Card CLI' (f59b8ee1-de54-48c6-837c-8001a555ccfa) successfully saved.
nmcli> quit
  1. Confirm the connection profile is created:
khadas@Khadas:~$ nmcli connection show
NAME                UUID                                  TYPE      DEVICE   
Wired connection 1  0325e9e9-b79f-35ef-b961-313bc9e1546d  ethernet  eth0     
Free SIM Card CLI   f59b8ee1-de54-48c6-837c-8001a555ccfa  gsm       cdc-wdm0 
Free-Mobile         1b25747a-4887-4d73-b2e8-944ae6cc3697  gsm       --       

Notice that the device assigned to the connection profile is the one displayed as type gsm on step 1. There was no need to set the connection.interface-name when creating said connection profile.
4. Make sure interface wwan0 is up, otherwise the activation of Mobile Data will fail:

ifconfig

If you see an interface whose name starts with wwan it means that you have a Wireless WAN network card and it's active (most likely already registered to the MNO of the nearest cellular tower). If nothing is displayed then run:

ifconfig -a

If you see an interface whose name starts with wwan it means that you have a Wireless WAN network card and it's NOT active. Run the following command to activate it:

khadas@Khadas:~$ sudo ifconfig wwan0 up

khadas@Khadas:~$ ifconfig | grep wwan
wwan0: flags=4291<UP,BROADCAST,RUNNING,NOARP,MULTICAST>  mtu 1416

If no interface name starting with wwan was displayed it could mean that there is no 4G LTE modem connected or it's not recognized or it's named differently.
5. Now everything is ready. Connect using the connection profile created and the corresponding interface:

khadas@Khadas:~$ sudo nmcli connection up f59b8ee1-de54-48c6-837c-8001a555ccfa ifname cdc-wdm0
Connection successfully activated (D-Bus active path: /org/freedesktop/NetworkManager/ActiveConnection/30)
  1. Confirm there's Internet by sending a ping through wwan0 interface:
khadas@Khadas:~$ ping www.khadas.com -I wwan0
PING td-ccm-neg-87-45.frsdns.net (55.66.77.88) from 10.78.112.64 wwan0: 56(84) bytes of data.
64 bytes from 11.22.33.44.bc.googleusercontent.com (55.66.77.88): icmp_seq=1 ttl=116 time=253 ms
64 bytes from 11.22.33.44.bc.googleusercontent.com (55.66.77.88): icmp_seq=2 ttl=116 time=63.3 ms
64 bytes from 11.22.33.44.bc.googleusercontent.com (55.66.77.88): icmp_seq=3 ttl=116 time=39.8 ms
64 bytes from 11.22.33.44.bc.googleusercontent.com (55.66.77.88): icmp_seq=4 ttl=116 time=56.3 ms
64 bytes from 11.22.33.44.bc.googleusercontent.com (55.66.77.88): icmp_seq=5 ttl=116 time=44.0 ms
64 bytes from 11.22.33.44.bc.googleusercontent.com (55.66.77.88): icmp_seq=6 ttl=116 time=40.1 ms
64 bytes from 11.22.33.44.bc.googleusercontent.com (55.66.77.88): icmp_seq=7 ttl=116 time=38.9 ms
64 bytes from 11.22.33.44.bc.googleusercontent.com (55.66.77.88): icmp_seq=8 ttl=116 time=39.0 ms
64 bytes from 11.22.33.44.bc.googleusercontent.com (55.66.77.88): icmp_seq=9 ttl=116 time=37.2 ms
^C
--- td-ccm-neg-87-45.frsdns.net ping statistics ---
9 packets transmitted, 9 received, 0% packet loss, time 8013ms
rtt min/avg/max/mdev = 37.222/68.010/253.465/66.115 ms

Run the command below whenever you need to disconnect:

khadas@Khadas:~$ sudo nmcli connection down f59b8ee1-de54-48c6-837c-8001a555ccfa ifname cdc-wdm0

In case Data Roaming is needed, Check later because I don't know how to do it yet!


Tips & tricks:

Disable wwan (Mobile Network)

khadas@Khadas:~$ sudo nmcli radio wwan off

Enable wwan (Mobile Network)

khadas@Khadas:~$ sudo nmcli radio wwan on

Display all network interfaces (active and inactive)

ifconfig -a

Display status of devices

nmcli dev status

List all connection profiles

nmcli connection show

Get details of a specific connection profile

nmcli connection show <connection_profile_UUID>

Sources: