squeak-phone/devices/pine64-pinephone/modem-docs/Modem on PinePhone.html

105 lines
8.8 KiB
HTML
Raw Permalink Blame History

This file contains invisible Unicode characters

This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

<!DOCTYPE html>
<html><head>
<meta http-equiv="content-type" content="text/html; charset=UTF-8"><meta charset="utf-8"><meta name="viewport" content="width=device-width, initial-scale=1"><meta name="referrer" content="no-referrer"><link rel="stylesheet" href="Modem%20on%20PinePhone_files/style.css"><title>Modem on PinePhone</title></head><body><header><div class="title"><a href="https://xnux.eu/index.html">xnux.eu</a> - <a href="https://xnux.eu/map.html">site map</a> - <a href="https://xnux.eu/news.html">news</a></div></header><main><section><h1 id="toc-modem-on-pinephone">Modem on PinePhone</h1><div style="float:right"><a href="https://xnux.eu/contribute.html"><img src="Modem%20on%20PinePhone_files/contrib.png" style="vertical-align: middle"> Contribute</a></div><p><a href="https://www.quectel.com/product/eg25g.htm" class="external">Quectel
EG25-G</a> modem in PinePhone handles WWAN, GPS and celular services. It is
based on <code>Qualcomm MDM 9607</code> chipset, has 256&nbsp;MiB DRAM, 256&nbsp;MiB
NAND, and a single Cortex-A7 CPU clocked up to 1.3GHz.</p><p>The
modem's&nbsp;fir­mware is split into two parts:</p><ul><li>Linux kernel + userspace
runs on an ARM CPU</li><li>Modem's&nbsp;fir­mware runs on Hexagon
ADSP</li></ul><p>Most AT commands are run on a separeate DSP processor cores
(Hexagon QDSP6 V5), with some being forwarded to a Linux userspace program
called <code>atfwd_daemon</code> running on the ARM&nbsp;CPU.</p><p>Reverse
engineering the exisintg software for ARM CPU inside the modem is quite easy
using ghidra. ADB unlocker was made this&nbsp;way.</p><h2 id="toc-modem-power-driver">Modem power driver</h2><p>My kernel is a bit
special, since it contains a special <a href="https://megous.com/git/linux/commit/?h=modem-5.8&amp;id=9e26fe7200672c64256652b916319873fd602ebf" class="external">modem power manager driver</a> (released 20200803 along
with Linux&nbsp;5.8).</p><p>My driver implements several features:</p><ul><li>it
ensures modem is configured properly for audio and&nbsp;sleep</li><li>it implements
airplane mode via rfkill interface</li><li>it implements modem
suspend/resume</li><li>it hides PinePhone variant differences</li><li>it
implements URC caching on all pinephone variants regardless of AP_READY
availability</li><li>it makes the modem sleep most of the time</li><li>it
handles powerup/po­werdown errors properly</li><li>it checks for killswitch and
reports it to userspace/dmesg</li><li>it doesn't waste time during powerdown and
waits for actual modem powerdown (it doesn't just sleep for a
fixed&nbsp;time)</li><li>it handles SoC wakeup on RI</li><li>it shuts down the modem
properly during kernel powerdown/re­boot to avoid data loss inside the
modem's&nbsp;NAN­D&nbsp;flash</li><li>it reports all errors to dmesg for easy
troublesho­oting/failu­re detection</li></ul><p>Enabling and disabling the
power to the modem is as simple&nbsp;as:</p><pre class="hl"><span class="hl
slc"># request powerup</span>
<span class="hl kwb">echo</span> <span class="hl
num">1</span> <span class="hl opt">&gt; /</span>sys<span class="hl
opt">/</span>class<span class="hl opt">/</span>modem<span class="hl
kwb">-power</span><span class="hl opt">/</span>modem<span class="hl
kwb">-power</span><span class="hl opt">/</span>device<span class="hl
opt">/</span>powered
<span class="hl slc"># request powerdown</span>
<span class="hl kwb">echo</span> <span class="hl num">0</span> <span class="hl
opt">&gt; /</span>sys<span class="hl opt">/</span>class<span class="hl
opt">/</span>modem<span class="hl kwb">-power</span><span class="hl
opt">/</span>modem<span class="hl kwb">-power</span><span class="hl
opt">/</span>device<span class="hl opt">/</span>powered
<span class="hl
slc"># read power status (changes only after power state transition is complete)</span>
<span class="hl kwc">cat</span> <span class="hl opt">/</span>sys<span class="hl
opt">/</span>class<span class="hl opt">/</span>modem<span class="hl
kwb">-power</span><span class="hl opt">/</span>modem<span class="hl
kwb">-power</span><span class="hl opt">/</span>device<span class="hl
opt">/</span>powered
</pre><p>So there's&nbsp;no need to mess with gpios via
sysfs.</p><h2 id="toc-connecting-to-the-modem">Connecting to the
modem</h2><p>You can connect to the modem once it's&nbsp;powered up via:</p><pre class="hl">screen <span class="hl opt">/</span>dev<span class="hl
opt">/</span>ttyUSB2 <span class="hl num">115200</span>
</pre><p>Disconnect by
<code>CTRL+a k</code>.</p><h2 id="toc-setting-up-the-modem-for-voice-calling">Setting up the modem for voice
calling</h2><p>Once per a lifetime you have to run
<code>AT+QDAI=1,0,0,2,0,1,1,1</code> and reboot the modem. That will configure
audio on the modem side correctly and store the configuration persistently
inside the modem. This is not necessary if you use my modem driver.</p><p>To
setup audio for call use my <a href="https://xnux.eu/devices/feature/audio-pp.html">call audio setup
program</a>.</p><p>You need to run the program after the call starts twice. Once
with your desired audio setup without <code>-2</code> option and once with
<code>-2</code> option.</p><p>To answer a call type <code>ATA</code>, to make a
call <code>ATDsomenumber;</code>, to hangup <code>ATH</code>.</p><p>That's&nbsp;it.
;)</p><h2 id="toc-modem-reverse-engineering">Modem reverse
engineering</h2><p>See <a href="https://xnux.eu/devices/feature/modem-pp-reveng.html">this page for
details</a>.</p><h2 id="toc-unlock-adb-access">Unlock ADB
access</h2><p>It's&nbsp;possible to access the Linux side of the modem via adb, or
reboot the modem to fastboot mode and boot your own kernel, The modem is rooted
by default, and you can install and run your own software inside the modem.
It's&nbsp;possible to communicate between A64 and the modem's&nbsp;ARM CPU via USB
serial port (ttyGS0 on modem side and ttyUSB1 on&nbsp;A64).</p><p>It's&nbsp;also
possible to create your own URCs up to 128B in size by sending them as a
datagram message to UNIX socket <code>/tmp/.urc_sock</code>. See <a href="https://xnux.eu/devices/feature/urc.c" class="file">urc.c</a>.</p><p>To install your own program on the modem
persistently you need to remount modem's&nbsp;root filesystem read write and install
your program somewhere in <code>/usr/bin</code>. Add your startup script to
<code>/etc/init.d</code>.</p><p>To get <code>adb</code> access to the
modem:</p><ul><li>Get adb key via <code>AT+QADBKEY?</code></li><li>Enter the adb
key to the <a href="https://xnux.eu/devices/feature/qadbkey-unlock.c" class="file">unlocker
utility</a></li><li>Follow the instructions from the
<code>qadbkey-unlock</code></li><li>Install or get <code>adb</code> for your
distribution</li><li><code>adb shell</code> should get you a root shell on
the&nbsp;modem</li><li><code>adb pull</code> and <code>adb push</code> can be used
to copy files to/from the&nbsp;modem</li></ul><p>On Arch Linux ARM, adb is no longer
supported, so you need to compile it from source code. You can use <a href="https://github.com/qhuyduong/arm_adb" class="external">https://github.com/…uong/arm_adb</a> with <a href="https://xnux.eu/devices/feature/0001-Fix-build-on-modern-Arch-Linux.patch" class="file">this patch</a> to
make it work with current <code>openssl</code>.</p><h2 id="toc-modem-power-management">Modem power management</h2><p>Various PinePhone
variants have SoC GPIOs routed to the modem differently. So you need to be aware
of what PinePhone variant you have, when experimenting with
the&nbsp;modem.</p><p>Power management comes down to:</p><ul><li>letting the modem
sleep when it's&nbsp;not in use, and waking it up when it's&nbsp;needed for
something,</li><li>and letting the host sleep, and configure the modem to wake
the host up, when some important event happens (incomming call,
sms,&nbsp;…).</li></ul><p>Summay of modem's&nbsp;be­havior related to
powerup/po­werdown and power management:</p><ul><li>powerup takes about 14s,
unless the modem is too hot (&gt;5060°C), then it may take as long as 22s
due to CPU inside the modem being downclocked from 1.3Ghz
to&nbsp;400MHz</li><li>configuration of the physical UART and ttyUSB2 is shared for
some reason, so ATE0 issued on UART will turn echo off also on
ttyUSB2</li><li>modem sleeps when an election process based on the status of USB
port, DTR pin, etc. results in a positive decision</li><li>modem disables RF
based on #W_DISABLE only when configured to do so
via&nbsp;<code>AT+QCFG="airplanecontrol"</code></li><li>modem wakes up the host via
USB or RI pin based on&nbsp;<code>AT+QCFG="risignaltype"</code></li><li>modem will
cache URCs based on <code>AP_READY</code> pin's&nbsp;status only when
<code>AT+QCFG="apready"</code> is configured</li><li>powerdown takes about the
same time as powerup</li></ul></section></main><footer><p>E-mail: <a href="mailto:x@xnux.eu">x@xnux.eu</a> - <a href="https://xnux.eu/map.html" accesskey="m">site map</a> - <a href="https://xnux.eu/rss.xml">RSS</a></p></footer></body></html>