AcousticBorn¶
sweep.equations.AcousticBorn ¶
Bases: sweep.equations.base.SecondOrderEquation
Second-order 2-D acoustic Born / LSRTM wave equation.
Two coupled scalar wave equations: a background pressure-like field
h1 propagating through the smooth velocity vp, and a
scattered pressure-like field sh1 driven by the reflectivity
perturbation mp acting on the background Laplacian (linearised
Born scattering). Both fields share an independent set of CPML
memory variables. Defaults: source on the background field h1,
receivers on the scattered field sh1 — the standard layout for
least-squares reverse-time migration.
With impl='c' the gradient of vp is the reflection (RWI)
tomographic one of Wu & Alkhalifah (2015), terms II+III+IV, in the
full and boundary-saving modes. It is computed only when vp
requires grad -- it doubles the backward and up to doubles its
memory -- so an LSRTM with a fixed vp runs the reflectivity-only
path at the old cost.
Models (constructor input order)
vp(m/s): Background acoustic velocity model.mp: Acoustic reflectivity perturbation used for LSRTM.
Wavefields
h1(aliases:pressure,p,background): Background acoustic pressure-like wavefield; default source.h2(aliases:pressure_prev,background_prev): Previous-step background wavefield (internal).psix: Background CPML memory variable for the x-derivative term (internal).psiz: Background CPML memory variable for the z-derivative term (internal).zetax: Background CPML auxiliary wavefield for the x-direction update (internal).zetaz: Background CPML auxiliary wavefield for the z-direction update (internal).sh1(aliases:scattered,scattered_pressure,data): Scattered acoustic wavefield used for LSRTM data prediction; default receiver.sh2(aliases:scattered_prev): Previous-step scattered wavefield (internal).spsix: Scattered-wave CPML memory variable for the x-derivative term (internal).spsiz: Scattered-wave CPML memory variable for the z-derivative term (internal).szetax: Scattered-wave CPML auxiliary wavefield for the x-direction update (internal).szetaz: Scattered-wave CPML auxiliary wavefield for the z-direction update (internal).
Defaults
source_type:['h1']receiver_type:['sh1']pml_type:'cpmlr'
Build the 2-D acoustic LSRTM equation operator.
Parameters:
-
spatial_order–FD accuracy order of the spatial Laplacians applied to both the background and scattered fields — e.g.
spatial_order=4is fourth-order accurate. Internally the half-stencil width isM = spatial_order // 2(used for loop bounds and PML padding). Must be an even integer (2, 4, 6, 8, 10, …). Performance note (impl='c'on CUDA): the compiled kernels ship template specialisations only forspatial_order ∈ {2, 4, 6, 8}. Above 8 the dispatcher drops to a generic runtime path (order = -1insrc/sweep/csrc/cuda/equations/acoustic_born2d/forward.cu) which uses more registers and runs noticeably slower. The PyTorch eager path is unaffected. Defaults to 4. -
device–Device for the operator's static kernels. Use
'cuda'/ atorch.devicefor GPU runs so the propagator can follow without a host↔device copy. Defaults to'cpu'. -
backend–Array / programming backend,
'torch'or'jax'. When you later wantimpl='c', leave this on'torch'. Defaults to'torch'.
C_NAME
class-attribute
¶
str(object='') -> str str(bytes_or_buffer[, encoding[, errors]]) -> str
Create a new string object from the given object. If encoding or errors is specified, then the object must expose a data buffer that will be decoded using the given encoding and error handler. Otherwise, returns the result of object.str() (if defined) or repr(object). encoding defaults to sys.getdefaultencoding(). errors defaults to 'strict'.
c_refuse_grads ¶
c_refuse_grads(
wavelet_grad,
model_grad_mask,
boundary_saving=False,
boundary_dtype=None,
checkpoint=False,
)
impl='c': the wavelet gradient, and vp's in the checkpoint modes, are refused (refuse_c_grads).
cuda_layout_for_grads ¶
The layout of a call whose models need these gradients
(grad_mask[i]: model i requires grad; None: all of them).
Term III on its own¶
Wu & Alkhalifah (2015, eq. 18-20) weight the image-point term III of the RWI
velocity gradient separately: (II+IV) + beta*III. Set
SWEEP_LSRTM_SPLIT_III=1 and the impl='c' full or boundary-saving backward
of AcousticBorn / AcousticBorn3D puts II+IV in vp.grad and keeps III
aside, on the same grid:
import os
from sweep.propagator import last_grad_split_iii
os.environ["SWEEP_LSRTM_SPLIT_III"] = "1" # read by every backward
loss.backward()
grad_vp = vp.grad + beta * last_grad_split_iii()
Without the switch vp.grad holds II+III+IV. The checkpointing modes return
no vp gradient, split or not. last_grad_split_iii() returns None until a
split backward has run, and afterwards the III of the most recent one.
Notebook 32 shows
the split on the paper's Figure 1 setup.
sweep.propagator.last_grad_split_iii ¶
Term III of the last split LSRTM backward, on the model grid, or None.
Only populated with SWEEP_LSRTM_SPLIT_III=1 on AcousticBorn /
AcousticBorn3D in the full or boundary-saving mode; vp.grad then holds
II+IV, so the paper's weighted gradient is vp.grad + beta * III.