== Sparse Matrix-Vector Multiplication == In this example, we verify the functional correctness of a matrix-vector multiplication routine where the matrix is represented in a sparse (Compressed Sparse Row) representation. File `csr.h`: {{{ #ifndef _CSR_H #define _CSR_H /* Compressed Sparse Row (CSR) sparse matrix representation. */ struct csr_matrix { double *val; // length NZ (number of non-0s) int *col_ind; // length NZ int *row_ptr; // length N+1. row_ptr[N]=NZ. int rows, cols; // number of rows (N), number of columns }; /* Multiplies matrix m and (dense) vector v, storing result in already allocated vector p. If m has dimensions NxM then v has length M and p has length N. */ void csr_matrix_vector_multiply(struct csr_matrix *m, double *v, double *p); #endif }}} File `csr.c`: {{{ /* Implementation of CSR matrix-vector multiplication from "LAProof: A Library of Formal Proofs of Accuracy and Correctness for Linear Algebra Programs" by Kellison, Appel, Tekriwal, and Bindel, IEEE 30th Symposium on Computer Arithmetic, 2023. That paper cites Barrett et al., "Templates for the Solution of Linear Systems: Building Blocks for Iterative Methods", SIAM, 1994, as the source of the algorithm. */ #include "csr.h" #define fma(x,y,s) (x*y+s) void csr_matrix_vector_multiply(struct csr_matrix *m, double *v, double *p) { int i, rows=m->rows; double *val = m->val; int *col_ind = m->col_ind; int *row_ptr = m->row_ptr; int next=row_ptr[0]; for (i=0; i #include #include #include "csr.h" typedef struct $mat { int n, m; // num rows, columns; double data[][]; } $mat; void $mat_vec_mul($mat mat, double * v, double *p) { int n = mat.n, m = mat.m; for (int i=0; i