Huawei E3531 configuration Raspbian Jessie

This post describes the configuration I used on raspbian Jessie lite to get a Huawei E3531 working with the o2(uk) carrier. After searching a lot over the forums and google it was difficult to determine the correct way to do this using raspbian with this particular model of modem and the problems I was experiencing. The first hurdle was getting usb_modeswitch working correctly to switch the usb modem from mass storage mode into modem mode. The second hurdle was configuring pppd to set up the modem correctly and make a ppp connection to o2.

The first problem was usb_modeswitch not being run or failing to switch the dongle into modem mode.

The second problem was pppd connecting and successfully getting past authentication but then receiving modem hangups after LCP compression negotiation (if that’s the right term?).

In the end the solution to get this working was from a mixture of posts and manpages and a little bit of hacking. There are two sections to this, usb_modeswitch which describes how to get usb_modeswitch working with udev (the kernel event handler). The second section pppd is the actual configuration of pppd to set up the modem and dial to create the ppp connection.

usb_modeswitch

Usually when a 3G USB dongle is inserted it starts up in mass storage mode that gives you access to pre-loaded windows drivers stored on the device. When installed these drivers then send a specific packet to the modem to switch the mode into the modem mode. In the case of the Huawei E3531 under windows for simplicity there is a third mode which runs the HiLink firmware on the dongle. What HiLink does is present a LAN interface on windows much like a USB to Ethernet adapter. This interface then acts as if you’ve connected the Ethernet port to a modem/router where you can navigate to 192.168.6.254 on your favorite browser and view usage, signal strength messages etc. A dhcp server issues the dns and default route addresses to get out onto the mobile broadband network. For casual use HiLink is probably good enough but this additional layer of complexity is not required for small projects.

What usb_modeswitch does is send the special packet to the usb dongle which causes the mode to switch. Once the dongle has switched to change modes again it needs to be unplugged and plugged back in again so that it starts in mass storage mode.

For the Huawei you can tell which mode the device is in by using lsusb, if usb_modeswitch hasn’t already changed the mode (as in my case) there will be a line reported somewhere like:

pi@raspberrypi:~ $ lsusb
Bus 001 Device 004: ID 12d1:1f01 Huawei Technologies Co., Ltd.

ID 12d1:1f01 identifies mass storage mode, modem mode for this dongle is identified by ID 12d1:1001 and HiLink mode is ID 12d1:14dc.

usb_modeswitch is installed through the usual way by apt-get, in Raspbian jessie it was already available but as noted before nothing happend after the device was plugged in. There is a way to manually switch this device through the command line:

sudo usb_modeswitch -W -I -v 12d1 -p 1f01 -M 55534243123456780000000000000011062000000101000100000000000000

sudo usb_modeswitch -W -I -v 12d1 -p 1f01 -M 55534243123456780000000000000011062000000100000000000000000000

The first command switches it into HiLink mode and the second command switches the device into modem mode where /dev/ttyUSB0, /dev/ttyUSB1, /dev/ttyUSB2 is created to communicate through the modem with AT commands. AT commands configure the modem much like the common conexant dial up modems. There are a vast variety of commands to get RSSI info and much more. You can also send/receive text messages, a little on that in a later post.

Using the second command you should see the output, lsusb result and tty devices:

pi@raspberrypi:~ $ sudo usb_modeswitch -W -I -v 12d1 -p 1f01 -M 55534243123456780000000000000011062000000100000000000000000000
Take all parameters from the command line

* usb_modeswitch: handle USB devices with multiple modes
* Version 2.2.0 (C) Josua Dietze 2014
* Based on libusb1/libusbx

! PLEASE REPORT NEW CONFIGURATIONS !

DefaultVendor= 0x12d1
DefaultProduct= 0x1f01
MessageContent="55534243123456780000000000000011062000000100000000000000000000"
NeedResponse=0

InquireDevice=1

Look for default devices ...
found USB ID 12d1:1f01
vendor ID matched
product ID matched
found USB ID 0424:ec00
found USB ID 0424:9514
found USB ID 1d6b:0002
Found devices in default mode (1)
Access device 007 on bus 001
Current configuration number is 1
Use interface number 0
Use endpoints 0x01 (out) and 0x81 (in)
Inquire device details; driver will be detached ...
Looking for active driver ...
OK, driver detached

SCSI inquiry data (for identification)
-------------------------
Vendor String: HUAWEI
Model String: Mass Storage
Revision String: 2.31
-------------------------

USB description data (for identification)
-------------------------
Manufacturer: HUAWEI
Product: HUAWEI Mobile
Serial No.: FFFFFFFFFFFFFFFF
-------------------------
Set up interface 0
Use endpoint 0x01 for message sending ...
Trying to send message 1 to endpoint 0x01 ...
OK, message successfully sent
Reset response endpoint 0x81
Reset message endpoint 0x01
-> Run lsusb to note any changes. Bye!

pi@raspberrypi:~ $ lsusb
Bus 001 Device 008: ID 12d1:1001 Huawei Technologies Co., Ltd. E169/E620/E800 HSDPA Modem
Bus 001 Device 003: ID 0424:ec00 Standard Microsystems Corp. SMSC9512/9514 Fast Ethernet Adapter
Bus 001 Device 002: ID 0424:9514 Standard Microsystems Corp.
Bus 001 Device 001: ID 1d6b:0002 Linux Foundation 2.0 root hub
pi@raspberrypi:~ $ ls /dev/ttyUSB*
/dev/ttyUSB0 /dev/ttyUSB1 /dev/ttyUSB2

The serial devices show up in /dev which great, pppd can then be configured to use these devices. One question remains is why is this not auto matically switching?

On http://www.draisberghof.de/usb_modeswitch/ the developer’s site, it mentions:

/etc/usb_modeswitch.d – a folder for customized config files. You can put new or modified config files here; they will take precedence over the collection of configurations in /usr/share/usb_modeswitch.”

On insertion of the USB dongle Udev should run usb_modeswitch and looking through syslog usb_modeswitch is being run, more worringly repeatedly. It first looked like usb_modeswitch does not recognise this device so I created the config file in usb_modeswitch.d below.

"/etc/usb_modeswitch.d/12d1:1f01"

DefaultVendor=0x12d1
DefaultProduct=0x1f01
MessageContent="55534243123456780000000000000011062000000100000000000000000000"
NoDriverLoading=1

This config file worked by manually running usb_modeswitch but not when inserting the dongle.

pi@raspberrypi:~ $ usb_modeswitch -c /etc/usb_modeswitch.d/12d1:1f01

Without investigating further as to why usb_modeswitch wasn’t automatically running and changing modes, since I’m not familiar with the internals of udev and usb_modeswitch, I hacked a little script in the home directory to get udev to run 15s after inserting the device so that usb_modeswitch isn’t required to be run manually. This script will take the usb ID from udev and run the config file saved in /etc/usb_modeswitch.d/. 

#!/bin/bash

CONFIG=/etc/usb_modeswitch.d/$1\:$2

sleep 15

usb_modeswitch -D -c $CONFIG

A udev rule is required to run this script, as a start a template was taken from /lib/udev/rules.d/40-usb_modeswitch.rules

"/etc/udev/rules.d/41-usb_modeswitch.rules"

ATTRS{idVendor}=="12d1", ATTR{bInterfaceNumber}=="00", ATTR{bInterfaceClass}=="08", RUN+="/home/pi/USBDevConnect %s{idVendor} %s{idProduct}"

The above rule runs /home/pi/USBDevConnect once on insertion of the E3531 and passes the vendor and product id to the script which the script uses as the config file. %s is a neat way to pass attributes to custom scripts.

Notice the use of sleep in USBDevConnect, I put this in to mimic the delay of manually running usb_modeswitch and the length is plucked out of thin air. Udev does have a limit of how long this script can run for, it seems 30s is hardcoded and any longer the script will get killed by udev unfortunately.

Using the above hack will get the E3531 to switch on insertion and at reboot. The next section will describe connecting to the internet via pppd.

pppd

See part 2 – pppd

Conclusion

This has turned into a two part post as the workaround to get usb_modeswitch working was long. A workaround has been proposed but please note this usb modem was configured with raspbian jessie lite, at the time of writing raspbian stretch was available and it had not been verified that the usb_modeswitch fix in the first post was still necessary. If you try this with raspbian stretch you may find that usb_modeswitch works correctly when the modem is inserted the first time.

See part 2 – pppd to get to the configuration of dialing the modem and establishing a point to point connection.

 

Leave a Reply