cancel
Showing results for 
Search instead for 
Did you mean: 

ST87M01 MQTT issues

iLabs
Associate

Module / setup
- Module: ST87M01-1301
- Host: STM32-class MCU over UART, 115200 8N1, no flow control
- Carrier: 1NCE NB-IoT (auto-PDP on CID 5)
- AT manual reference: v3.1, 2025-10-06

Current sleep-related configuration
16:34:39.720 -> === AT readbacks ===
16:34:39.720 -> >>> AT+CGMR
16:34:39.720 -> <<< A:2.7.0-M:2.7.0-S:2.7.0
16:34:39.720 -> <<< OK
16:34:39.720 -> >>> AT#SLEEPMODE?
16:34:39.720 -> <<< #SLEEPMODE: 1,5,0
16:34:39.720 -> <<< OK
16:34:39.720 -> >>> AT#WAKEUPEVENT?
16:34:39.720 -> <<< #WAKEUPEVENT: 15,3
16:34:39.720 -> <<< OK
16:34:39.720 -> >>> AT#SLEEPIND?
16:34:39.720 -> <<< #SLEEPIND: 0C
16:34:39.720 -> <<< OK
16:34:39.720 -> >>> AT#RINGPIN?
16:34:39.720 -> <<< #RINGPIN:0,20,1,100
16:34:39.720 -> <<< OK
16:34:39.720 -> >>> AT+CPSMS?
16:34:39.847 -> <<< +CPSMS: 1,,,"10010100","00001111"
16:34:39.847 -> <<< OK
16:34:39.847 -> >>> AT+CEDRXRDP
16:34:39.847 -> <<< +CEDRXRDP: 5,"0010","0010","0011"
16:34:39.847 -> <<< OK
16:34:39.847 -> === end dump ===

Observed behaviour

Use case: an MQTT client (using native AT#MQTT*) publishes a short message every 30 seconds to broker.hivemq.com:1883 (port 1883, no TLS). The
MQTT session and IP context stay up across the publish interval. Between publishes there is no AT activity from the host.

We observe two distinct failure modes:

Failure mode A: #SLEEP URC arrives after the command is sent, no response from module

16:14:46.658 <<< OK (previous MQTTPUB OK)
16:15:15.535 >>> AT#MQTTPUB=st87m01/data,hello #3,10,0,0 (29 s later)
16:15:22.679 <<< #SLEEP (7 s after our send)
16:15:46.666 <<< #WAKEUP (31 s after our send)
16:15:46.666 Publish failed (no OK in 30 s)
16:15:46.666 >>> AT#MQTTPUB=st87m01/data,hello #4,10,0,0
16:15:46.765 <<< OK (99 ms — succeeds)

The module accepted the AT#MQTTPUB bytes, then went to sleep without responding. #SLEEP arrived 7 s after our send. #WAKEUP arrived 31 s after our
send (apparently a natural wake — we did nothing). The very next AT#MQTTPUB, issued immediately after #WAKEUP, succeeded in 99 ms.

Failure mode B: module sleeps silently — no #SLEEP or #WAKEUP URC at all

In a separate run on the same hardware/firmware, after a different boot, with the same publish cadence, the module exhibited the following pattern
across many publish cycles without ever emitting a #SLEEP or #WAKEUP URC:

16:22:07.317 Publish: hello #2
16:22:07.317 >>> AT (sent as a "wake probe")
(no response for ~2 s — first AT lost)
16:22:09.303 >>> AT (second probe)
16:22:09.303 <<< OK (immediate — module is now responsive)
16:22:09.303 >>> AT#MQTTPUB=st87m01/data,hello #2,10,0,0
16:22:09.435 <<< OK (132 ms — succeeds)

The first AT after the 30 s quiet interval always gets no response; the second AT always responds immediately. Once the module is responsive,
AT#MQTTPUB succeeds in ~100 ms.

What we tried

1. Waited up to 30 s on AT#MQTTPUB — confirms there is no late response from the module; the OK truly never comes.
2. Two-step "wake probe": send AT twice with a 2 s gap before AT#MQTTPUB. This works reliably in both failure modes — but adds 2 s overhead per
publish when the module is asleep.
3. URC-based sleep tracking on the host: set a _sleeping flag from #SLEEP/#WAKEUP URCs and run a wake sequence only when flagged. Works in failure
mode A only when the #SLEEP URC arrives before the next host command, which is not guaranteed. Useless in failure mode B because no URCs are
emitted at all.

Questions

1. Is the first-byte-after-sleep loss documented? Per the manual, AT#PWROFF describes "wake by power-on key or UART character", and the CMUX <T3>
parameter mentions a wake response timer up to 10 s. Is there an analogous response-timer behaviour for the normal sleep mode? What is the minimum
number of bytes / time the host should send before issuing a real AT command after the module has been idle?
2. Is a host-side wake handshake documented anywhere? I have not found one in the AT manual, MQTT app note, or Startup app note. Is the
recommended pattern: send a dummy byte, wait N ms, then send the actual command? If so, what is N?
3. #SLEEP and #WAKEUP URC reliability. Are these URCs guaranteed to be emitted when the module enters/exits sleep, given AT#SLEEPIND is enabled
and saved? We observe runs where they are emitted (failure mode A) and runs where they are silently absent (failure mode B). What controls this?
4. Module accepting a command then sleeping without responding. In failure mode A the module clearly receives the bytes (it doesn't emit #WAKEUP,
which suggests it was already awake), but then goes to sleep without ever acknowledging the command. Is this a known scenario? Is the in-flight
command dropped or queued?
5. Default <hold_time> for AT#SLEEPMODE. The manual specifies the parameter but not its default value. What is the factory default? Our observed
timing (sleep hold ≈ 27–30 s) appears to match the default.
6. AT#RINGPIN for URC delivery. Would configuring AT#RINGPIN change the timing of #SLEEP/#WAKEUP URC delivery to the host? Our reading is that it
gives the host advance hardware notice before any URC, which would help on the receive side — but does it also change when the URC is emitted from
the module's perspective?
7. Recommended pattern for periodic publishing (≥ hold_time interval). What is ST's recommended sequence when the host wants to send an MQTT
publish (or any AT command) after an idle period longer than <hold_time>? Should the host explicitly issue something like AT#WAKEUP (if such a
command exists) or rely on UART activity to wake the module?

Any pointer to documentation we may have missed would be appreciated.

Thanks.

0 REPLIES 0