Y YASPS
Docs menu
Getting started Scene Mesh Primitive Primitive union Connectivity Attribute Minimizer Solver Differentiator Matrix Jacobian Hessian Gradient Examples Dropping in a container Cubify Inverse simulation

API reference · 08

Solver

Select a linear solver implementation, solve a block-sparse system Hx = g, where H is a symmetric positive semi-definite matrix, and g is the right-hand side vector.

solver

solver(solver="mas", **options)

Create a dispatcher around one of the supported linear solvers.

Parameter Type Default Description
solver str "mas" Implementation name: "mas" or "jacobian".
**options keyword arguments none MAS options. The jacobian implementation accepts no options.
Name Description Options
"mas" Multilevel additive Schwarz preconditioned conjugate gradient. Accepts the MAS options below.
"jacobian" Original block-Jacobi preconditioned conjugate gradient. No constructor options.

MAS options

The defaults are the effective values used by solver("mas", ...). Start with solver() and change these only when you need to tune a particular system. All integer capacities, schedules, intervals, and weights must be positive unless their description says otherwise.

Hierarchy construction

Option and type Default Description
max_domain_dofs
int or None
None Maximum scalar degrees of freedom in a local domain. None selects the larger of 48 and the largest variable dimension.
max_levels
int or None
None Maximum hierarchy depth. None selects 6.
target_nodes_per_partition
int or None
None Target node count passed to METIS for each partition. None selects 8.
minimum_domains_for_next_level
int
0 Stop adding coarse levels once the hierarchy is below this domain count. 0 disables this cutoff.
global_coarse_domain
bool
True Combine the final level into one domain when it fits the domain capacity. This preserves couplings between static components introduced by dynamic blocks.
domain_dof_schedule
tuple[int, ...] or None
None Per-level overrides for max_domain_dofs. The last value is reused for later levels.
target_node_schedule
tuple[int, ...] or None
None Per-level overrides for target_nodes_per_partition. The last value is reused for later levels.

Solve policy and level weights

Option and type Default Description
solve_mode
str
"mas_pcg" "mas_pcg" solves the full system with MAS-preconditioned CG. "reduced_then_fine" solves the coarsest system first, prolongates it, then runs a bounded fine correction.
fine_correction_iterations
int
8 Maximum fine-level iterations in "reduced_then_fine" mode. May be 0.
inverse_backend
str
"cooperative_gauss_jordan" Local inverse backend: "cooperative_gauss_jordan", "cooperative_spd_inverse", or "cpu_reference". The CPU backend forces the host solve path.
coarsest_level_weight
float
2.5 Weight for the coarsest level when YASPS generates level weights automatically.
level_weights
tuple[float, ...] or None
None Explicit positive weight for every hierarchy level. None uses 1.5 on the finest level, 1.0 on intermediate levels, and coarsest_level_weight on the last level.
duplicate_level_weight
float
0.5 Contribution weight for nodes represented at more than one hierarchy level. Must be between 0 and 1.

Dynamic blocks and collision tuning

Option and type Default Description
dynamic_edge_domains
bool
False Add local domains assembled from active dynamic blocks, such as collision blocks.
dynamic_edge_block_ratio
float
0.0 Minimum ratio of dynamic blocks to fine-level nodes before dynamic edge domains activate. Must be non-negative; 0.0 activates them whenever dynamic blocks exist.
collision_aware_reorder
bool
False Update hierarchy representatives from the active collision graph on each numerical rebuild.
collision_merge_across_types
bool
False Allow collision-aware reordering to merge nodes with different variable type IDs.
adaptive_fine_level_weight
bool or None
None Raise the fine-level weight for dense collision systems. None enables this only when level_weights is not supplied.
dense_collision_block_ratio
float
0.1 Dynamic-block ratio at which adaptive fine-level weighting activates.
dense_collision_fine_level_weight
float
3.0 Minimum fine-level weight used after the dense-collision threshold is reached.
numeric_rebuild_interval
int
1 Maximum number of solves between numerical preconditioner rebuilds when no dynamic blocks are active.
dynamic_numeric_rebuild_interval
int
1 Maximum number of solves between numerical preconditioner rebuilds while dynamic blocks are active. Changes between active and inactive dynamic connectivity still force a rebuild.

CUDA execution

Option and type Default Description
cuda_threads_per_block
int
96 CUDA block size for local inverse kernels. Accepted values are 32, 64, 96, and 128.
cuda_fixed_inverse_bucket_size
int or None
None Pad every local inverse to one fixed size. None selects bucket sizes automatically; an explicit size must fit the largest local domain.
cuda_enable_inverse_fallback
bool
True Retry a failed CUDA Gauss-Jordan local inverse with the CUDA SPD inverse kernel.
mixed_spmv
bool
False Use FP32 matrix values for SpMV, then audit convergence with the original FP64 system and run a correction solve when needed.
mixed_spmv_tolerance_factor
float
1.0 Multiply the requested tolerance for the mixed-precision solve. Must be greater than 0 and at most 1.
allow_cpu_fallback
bool
False Fall back to the host solve path if CUDA execution fails. YASPS disables this by default so CUDA failures remain visible.

Example

adjoint_linear_solver = solver()
contact_linear_solver = solver(
  "mas",
  dynamic_edge_domains=True,
  collision_aware_reorder=True,
)

Returns: new solver.

Raises: ValueError for an unknown solver name; TypeError when jacobian receives options.

setSolver

setSolver(solver="mas", **options)

Reset the current implementation and select another one.

Parameter Type Default Description
solver str "mas" Implementation name: "mas" or "jacobian".
**options keyword arguments none MAS options. The jacobian implementation accepts no options.

Example

adjoint_linear_solver.setSolver("jacobian")

Returns: this solver.

computeSolution

computeSolution(active_matrix, right_hand_side, initial_guess, tolerance=1e-3, maxIterations=20000, zero_initial_guess=False)

Solve the device-resident linear system. The selected implementation stores the result in solution.

Parameter Type Default Description
active_matrix matrix or hessian required Numeric block-sparse system matrix. None produces a zero solution.
right_hand_side gradient or compatible YASPS vector required Device-resident right-hand side with one value per matrix row.
initial_guess pycuda.gpuarray.GPUArray, compatible vector, or None required Initial solution estimate. Ignored when zero_initial_guess=True.
tolerance float 1e-3 Convergence tolerance.
maxIterations int 20000 Maximum PCG iterations.
zero_initial_guess bool False Start from zero instead of initial_guess.

Example

error_code = adjoint_linear_solver.computeSolution(
  adjoint_hessian,
  right_hand_side,
  adjoint_initial_guess,
  tolerance=1e-5,
  maxIterations=20000,
  zero_initial_guess=True,
)
direction = adjoint_linear_solver.solution

Returns: non-negative int on convergence, negative int otherwise.

Raises: ValueError when dimensions do not match; TypeError when the right-hand side is incompatible with the selected implementation.

reset

reset()

Release cached solver state, solution buffers, hierarchy data, and statistics.

Example

adjoint_linear_solver.reset()

Returns: None.

Properties

Property Type Description
solverName str Selected implementation name: "mas" or "jacobian".
implementation masSolver or jacobianPCGSolver Selected implementation object.
solution pycuda.gpuarray.GPUArray Most recently computed solution; empty before a solve or after reset.
statistics dict Copy of the most recent solve statistics, including convergence and iteration data.