Issues with ZTE MF 823 as RED/Dialup interface

I have a ZTE MF 823 4G stick which was working on an older version of IPFire for quite a long time now on a Raspberry PI B+ board. Some time ago, after updating IPFire from version 2.19 (core update 120) to a newer version which required a fresh install, I noticed, that the stick was not working as expected on the new IPFire version. Not having time to debug the issue, I reverted everything back to the working version and everything was fine.
Now the Raspberry PI board died (problems with USB power continuously resetting connecting USB devices), and I had no other choice, than to pick up a newer Raspberry PI’s and try it again.
The problem I am facing (even with IPFire 2.25 - core update 145) is, that the ZTE stick gets a new random MAC address at every reboot. This prevents the network configuration from finding the red0 device, resulting in:
Bringing up the red0 interface…
Interface red0 doesn’t exist.
If I run setup, remove red0 and re-add it again, everything works fine until the next reboot.

There have been other forum posts in the past, but I think they never realized, what caused the error.
https://forum.ipfire.org/viewtopic.php?f=27&t=20589&p=122253&hilit=zte#p122253
and
https://forum.ipfire.org/viewtopic.php?f=6&t=15281&p=127695&hilit=zte#p127695

As I didn’t get anywhere with this issue, I searched for other ways to use the stick. I found, that by setting it to “FACTORY” mode, I can use it as a dialup modem. This change survives a power failure or reboot, but the issue I am facing here is that after successfully connecting, the ppp0 device cannot be bridged:
Jun 11 08:34:51 firepdg chat[14882]: timeout set to 3 seconds
Jun 11 08:34:51 firepdg chat[14882]: report (CONNECT)
Jun 11 08:34:51 firepdg chat[14882]: abort on (\nBUSY\r)
Jun 11 08:34:51 firepdg chat[14882]: abort on (\nNO ANSWER\r)
Jun 11 08:34:51 firepdg chat[14882]: abort on (\nRINGING\r\n\r\nRINGING\r)
Jun 11 08:34:51 firepdg chat[14882]: abort on (\nNO CARRIER\r)
Jun 11 08:34:51 firepdg chat[14882]: send (+++ATZ^M)
Jun 11 08:34:51 firepdg chat[14882]: send (AT+ZOPRT=5^M)
Jun 11 08:34:51 firepdg chat[14882]: send (+++ATZ^M)
Jun 11 08:34:52 firepdg chat[14882]: expect (OK)
Jun 11 08:34:52 firepdg chat[14882]: ATZ^M^M
Jun 11 08:34:52 firepdg chat[14882]: OK
Jun 11 08:34:52 firepdg chat[14882]: – got it
Jun 11 08:34:52 firepdg chat[14882]: send (ATH0^M)
Jun 11 08:34:52 firepdg chat[14882]: expect (OK)
Jun 11 08:34:52 firepdg chat[14882]: ^M
Jun 11 08:34:52 firepdg chat[14882]: AT+ZOPRT=5^M^M
Jun 11 08:34:52 firepdg chat[14882]: OK
Jun 11 08:34:52 firepdg chat[14882]: – got it
Jun 11 08:34:52 firepdg chat[14882]: send (ATM0^M)
Jun 11 08:34:52 firepdg chat[14882]: expect (OK)
Jun 11 08:34:52 firepdg chat[14882]: ^M
Jun 11 08:34:52 firepdg chat[14882]: ATZ^M^M
Jun 11 08:34:52 firepdg chat[14882]: OK
Jun 11 08:34:52 firepdg chat[14882]: – got it
Jun 11 08:34:52 firepdg chat[14882]: send (AT+ZCDRUN=8^M)
Jun 11 08:34:52 firepdg chat[14882]: send (AT+CGDCONT=4,“IP”,“iliad”,0,0^M)
Jun 11 08:34:52 firepdg chat[14882]: send (sleep 5^M)
Jun 11 08:34:52 firepdg chat[14882]: timeout set to 45 seconds
Jun 11 08:34:52 firepdg chat[14882]: expect (OK)
Jun 11 08:34:52 firepdg chat[14882]: ^M
Jun 11 08:34:52 firepdg chat[14882]: ATH0^M^M
Jun 11 08:34:52 firepdg chat[14882]: OK
Jun 11 08:34:52 firepdg chat[14882]: – got it
Jun 11 08:34:52 firepdg chat[14882]: send (dATDT99#^M)
Jun 11 08:34:52 firepdg chat[14882]: expect (CONNECT)
Jun 11 08:34:52 firepdg chat[14882]: ^M
Jun 11 08:34:52 firepdg chat[14882]: ATM0^M^M
Jun 11 08:34:52 firepdg chat[14882]: OK^M
Jun 11 08:34:52 firepdg chat[14882]: AT+ZCDRUN=8^M^M
Jun 11 08:34:52 firepdg chat[14882]: Close autorun state result(0:FAIL 1:SUCCESS):1^M
Jun 11 08:34:52 firepdg chat[14882]: ^M
Jun 11 08:34:52 firepdg chat[14882]: OK^M
Jun 11 08:34:52 firepdg chat[14882]: AT+CGDCONT=4,“IP”,“iliad”,0,0^M^M
Jun 11 08:34:52 firepdg chat[14882]: OK^M
Jun 11 08:34:52 firepdg chat[14882]: ATDT
99#^M^M
Jun 11 08:34:52 firepdg chat[14882]: CONNECT
Jun 11 08:34:52 firepdg chat[14882]: – got it
Jun 11 08:34:52 firepdg chat[14882]: send ()
Jun 11 08:34:52 firepdg pppd[14858]: Serial connection established.
Jun 11 08:34:52 firepdg pppd[14858]: Using interface ppp0
Jun 11 08:34:52 firepdg pppd[14858]: Connect: ppp0 <–> /dev/ttyUSB2
Jun 11 08:34:53 firepdg root: Could not find a bridged zone for ppp0
Jun 11 08:34:53 firepdg codel: Codel AQM has been enabled on ‘ppp0’.
Jun 11 08:34:53 firepdg pppd[14858]: CHAP authentication succeeded
Jun 11 08:34:53 firepdg pppd[14858]: CHAP authentication succeeded
Jun 11 08:34:55 firepdg vnstatd[1284]: Interface “ppp0” enabled.

This could be anything else, too, because I really have no experience with setting up dialup modems anymore :wink:

What could be done to prevent the stick from changing MAC address at every boot?
Is there a way to tell IPFire to ignore MAC address binding for the RED interface?
What is causing IPFire in dialup mode to not work as expected?

Bye,
Oskar

Nothing. This mac is generated by the Stick not by IPFire. But you can change in /var/ipfire/ethernet/settings
RED_DEV=red0 to RED_DEV=usb0 if the kernel detect the device as usb0 at next connection.

Wow, works like a charm! Thanks for the fast reply and for your awesome work with IPFire!