Finally got an RPi Pico to play with. Turns out that the 8, 16, and 32 bit memory access arrays, mem8, mem16, mem32, in the stm module are also in the machine module for both the stm and rpi pico python builds. I’m guessing this is the case for all ARM-based micropythons. So no need for assembler to twiddle control registers, just peek n poke.
>>> help('modules')
__main__ gc uasyncio/event ujson
_boot machine uasyncio/funcs uos
_onewire math uasyncio/lock urandom
_rp2 micropython uasyncio/stream ure
_thread onewire ubinascii uselect
_uasyncio rp2 ucollections ustruct
builtins uarray uctypes usys
ds18x20 uasyncio/__init__ uhashlib utime
framebuf uasyncio/core uio uzlib
Plus any modules on the filesystem
>>> import uos
>>> dir(uos)
['__class__', '__name__', 'remove', 'VfsLfs2', 'chdir', 'getcwd', 'ilistdir', 'listdir', 'mkdir', 'mount', 'rename', 'rmdir', 'stat', 'statvfs', 'umount', 'uname']
>>> uos.uname()
(sysname='rp2', nodename='rp2', release='1.14.0', version='v1.14 on 2021-02-05 (GNU 9.3.0 MinSizeRel)', machine='Raspberry Pi Pico with RP2040')
>>> import machine
>>> dir(machine)
['__class__', '__name__', 'ADC', 'I2C', 'PWM', 'PWRON_RESET', 'Pin', 'SPI', 'SoftI2C', 'SoftSPI', 'Timer', 'UART', 'WDT', 'WDT_RESET', 'bootloader', 'deepsleep', 'disable_irq', 'enable_irq', 'freq', 'idle', 'lightsleep', 'mem16', 'mem32', 'mem8', 'reset', 'reset_cause', 'soft_reset', 'time_pulse_us', 'unique_id']
>>> [hex(machine.mem32[x]) for x in range(0,16,4)]
['0x20041f00', '0xef', '0x35', '0x31']
Also, micropython appears to be coded as a little endian machine, as illustrated by the following code snippet. I believe this is programmable in the ARM architecture.
>>> [hex(machine.mem8[x]) for x in range(0,4)]
['0x0', '0x1f', '0x4', '0x20']
>>> hex(machine.mem32[0])
'0x20041f00'
# Just for fun, access the bytes high-to-low to match 32-bit output visually
>>> [hex(machine.mem8[x]) for x in range(3,-1, -1)]
['0x20', '0x4', '0x1f', '0x0']