SVE complex GEMM packing mispartitions rows at VL384 (QEMU)
Maintainer thường phản hồi trong vòng 1 ngày
Chưa có ai nhận issue này.
Đánh giá
- Độ khó
- 4/5
- Thời gian dự kiến
- 3-5 ngày
- Mức phù hợp với người mới
- 45/100
Hướng nghiên cứu
Start with the two named complex SVE packers, kernel/arm64/gemm_ncopy_complex_sve_v1x4.c and kernel/arm64/gemm_tcopy_complex_sve_v1x4.c, and trace how their full-vector and remainder bounds determine packed layout. Build OpenBLAS with the supplied commands, then run the provided C reproducer under QEMU at VL384 for both c and z. Done means the checked outputs and unused tail pass for the affected dispatch tables without regressing the other reported vector lengths.
Do mô hình lập chỉ mục viết ra từ nội dung của issue.
Mô tả
SVE complex GEMM packing mispartitions rows at VL384 (QEMU)
On OpenBLAS develop 277ef7801416412ee970873701fdf14d603d2c3f and release
v0.3.34, public CGEMM/ZGEMM calls give wrong results with forced ARMV8SVE,
A64FX and NEOVERSEV1 dispatch at SVE VL384 under QEMU 8.2.2 and 10.2.1.
The one-call reproducer below uses column-major NoTrans/NoTrans, alpha=1,
beta=0, N=K=2, and M=13 for c or M=7 for z. With zero-based row i,
A(i,h)=i+2h+1 and B=1, so every result has real part 2*i+4 and imaginary
part zero. It checks all requested outputs and the unused output tail.
These two vectors pass with ARMV8 and NEOVERSEV2 dispatch at VL384, and
with the affected tables at the other five tested lengths: 128, 256, 512,
1024 and 2048 bits. Original Reference BLAS v3.12.1 CGEMM/ZGEMM returns the
expected results on both emulators at all six tested lengths. These pass
statements describe these reduced vectors.
Suspected cause and distinct path
The complex SVE packers kernel/arm64/gemm_ncopy_complex_sve_v1x4.c
and kernel/arm64/gemm_tcopy_complex_sve_v1x4.c
use n & -sve_size to select full vectors. At VL384, the lane counts are
12 for float and 6 for double. Thus 13 & -12 = 4 and 7 & -6 = 2,
where floor-to-multiple counts would be 12 and 6. The full-vector loop
advances by the actual vector width, while the remainder uses the masked
bound, making the packed layout inconsistent.
The NoTrans/NoTrans complex calls reach the regular GEMM path and its
complex tcopy packer. These tables use the generic complex small-matrix
permit, whose executable body returns zero
(kernel/generic/zgemm_small_matrix_permit.c).
This report is deliberately anchored on C/Z calls: tiny real S/D GEMM
calls in this build enter separate small-matrix kernels and do not isolate
the regular real packers.
This count calculation is separate from the SYRK/SYR2K driver panel-split
problem in #6100.
Arithmetic division/remainder is a candidate direction; no source repair
has been implemented or tested for this report.
Hardware scope
The names above select OpenBLAS dispatch tables on QEMU's max CPU.
Documented maximum SVE lengths for the named processors are 128 bits for
Neoverse N2/V2, 256 bits for Neoverse V1, and 512 bits for A64FX
(Arm, NVIDIA).
SVE permits non-power-of-two multiples of 128 bits;
VL384 is an architectural conformance case supported by QEMU. These forced
table/VL combinations do not establish a failure on the named native
processors. Native confirmation is unavailable.
Reproduce
On Linux, use Git, GNU Make, host GCC, an AArch64 GCC cross toolchain
with its glibc sysroot, and QEMU user mode. GCC 15.2 was used for the
reported builds. Save the C block below as repro-complex.c in a clean
working directory, then run these commands from that directory:
git init openblas-src
git -C openblas-src fetch --depth=1 https://github.com/OpenMathLib/OpenBLAS.git 277ef7801416412ee970873701fdf14d603d2c3f
git -C openblas-src checkout --detach FETCH_HEAD
cd openblas-src
make -j4 ARCH=arm64 BINARY=64 TARGET=ARMV8 DYNAMIC_ARCH=1 \
'DYNAMIC_LIST=ARMV8SVE A64FX NEOVERSEV1 NEOVERSEN2' \
NOFORTRAN=1 NO_LAPACK=1 USE_THREAD=0 NUM_THREADS=1 HOSTCC=gcc \
CC=aarch64-linux-gnu-gcc AR=aarch64-linux-gnu-ar RANLIB=aarch64-linux-gnu-ranlib
make ARCH=arm64 BINARY=64 TARGET=ARMV8 DYNAMIC_ARCH=1 \
'DYNAMIC_LIST=ARMV8SVE A64FX NEOVERSEV1 NEOVERSEN2' \
NOFORTRAN=1 NO_LAPACK=1 USE_THREAD=0 NUM_THREADS=1 HOSTCC=gcc \
CC=aarch64-linux-gnu-gcc AR=aarch64-linux-gnu-ar RANLIB=aarch64-linux-gnu-ranlib \
PREFIX="$PWD/install" install
aarch64-linux-gnu-gcc -O2 -Wall -Wextra -Iinstall/include ../repro-complex.c \
install/lib/libopenblas.a -lm -lpthread -o complex-repro
OPENBLAS_CORETYPE=ARMV8SVE OPENBLAS_NUM_THREADS=1 \
qemu-aarch64 -L /usr/aarch64-linux-gnu \
-cpu max,sve-default-vector-length=48 ./complex-repro 384 c
Replace the final c with z for double complex. Repeat with QEMU
8.2.2's qemu-aarch64-static for the second emulator. The QEMU property
takes bytes: 48 requests VL384.
The program checks the actual vector length with PR_SVE_GET_VL and
prints the selected OpenBLAS core; confirm that the printed core matches
the requested dispatch table. Exit 0 means the checked values are right,
1 means a numerical or padding mismatch, and 2 means a setup/argument
failure rather than a valid numerical result. Each mode makes one public
BLAS call.
repro-complex.c
/* Public complex GEMM reduced from the VL384 packing search. */
#include <cblas.h>
#include <math.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/prctl.h>
int main(int argc,char **argv) {
int requested=argc>1?atoi(argv[1]):384;
int vl=prctl(51,0,0,0,0);
if(vl<0 || (vl&65535)*8!=requested)return 2;
int isdouble=argc>2&&!strcmp(argv[2],"z"),m=isdouble?7:13,n=2,k=2;
float af[256],bf[8],cf[256],alpha[2]={1,0},beta[2]={0,0};
double ad[256],bd[8],cd[256],alphad[2]={1,0},betad[2]={0,0};
for(int i=0;i<256;i++){af[i]=ad[i]=NAN;cf[i]=cd[i]=17;}
for(int h=0;h<k;h++)for(int i=0;i<m;i++){
af[2*(i+h*m)]=ad[2*(i+h*m)]=i+2*h+1;
af[2*(i+h*m)+1]=ad[2*(i+h*m)+1]=0;
}
for(int i=0;i<8;i++){bf[i]=bd[i]=(i&1)?0:1;}
for(int i=0;i<2*m*n;i++)cf[i]=cd[i]=NAN;
if(isdouble)cblas_zgemm(CblasColMajor,CblasNoTrans,CblasNoTrans,m,n,k,alphad,ad,m,bd,k,betad,cd,m);
else cblas_cgemm(CblasColMajor,CblasNoTrans,CblasNoTrans,m,n,k,alpha,af,m,bf,k,beta,cf,m);
int wrong=0;
for(int j=0;j<n;j++)for(int i=0;i<m;i++){
double actual=isdouble?cd[2*(i+j*m)]:cf[2*(i+j*m)],imag=isdouble?cd[2*(i+j*m)+1]:cf[2*(i+j*m)+1];
if(actual!=2*i+4 || imag!=0)wrong++;
}
for(int i=2*m*n;i<256;i++)wrong+=(isdouble?cd[i]:cf[i])!=17;
printf("COMPLEX-VL: %s precision=%c core=%s VL=%d m=%d n=2 k=2 last=%g want=%d wrong=%d first_surfaced_by=differential\n",
wrong?"WRONG":"RIGHT",isdouble?'z':'c',openblas_get_corename(),requested,m,
isdouble?cd[2*(m-1)]:cf[2*(m-1)],2*(m-1)+4,wrong);
return wrong?1:0;
}
First surfaced by differential testing (first_surfaced_by: differential).
- Ngôn ngữ chính
- C
- Star
- 7.6k
- Fork
- 1.7k
- Merge trung bình
- 1 ngày 11 giờ
- Pull request đã merge (30 ngày)
- 53
Chuẩn bị môi trường
Dự án này không cung cấp dev container, Dockerfile hay hướng dẫn đóng góp, nên bạn cần tự thiết lập môi trường: hãy bắt đầu từ README và xem hướng dẫn đóng góp lần đầu của chúng tôi để biết các bước chung.
Bắt đầu từ đâu
- Đọc hết issue, rồi đọc hướng dẫn đóng góp của dự án.
- Bình luận trên issue rằng bạn sẽ nhận — tránh hai người làm cùng một việc.
- Fork repository và làm thay đổi trên một nhánh.
- Mở pull request có tham chiếu số hiệu của issue.
Issue khác của OpenMathLib/OpenBLAS
-
Độ khó 5/5 Hơn một tuần Mức phù hợp với người mới 25/100
OpenMathLib/OpenBLAS#6119 · 2 bình luận ·
Maintainer thường phản hồi trong vòng 1 ngày
-
openblas_set_threads_callback_function is a silent no-op on WindowsCó thể đã có người làm @martin-frbg đã nhận 5 ngày trước. Đang mở
Độ khó 4/5 3-5 ngày Mức phù hợp với người mới 43/100
OpenMathLib/OpenBLAS#6108 · 2 bình luận · 1 reaction ·
Maintainer thường phản hồi trong vòng 1 ngày
-
Độ khó 4/5 3-5 ngày Mức phù hợp với người mới 43/100
OpenMathLib/OpenBLAS#6107 · 3 bình luận ·
Maintainer thường phản hồi trong vòng 1 ngày
-
Độ khó 4/5 3-5 ngày Mức phù hợp với người mới 58/100
OpenMathLib/OpenBLAS#6103 ·
Maintainer thường phản hồi trong vòng 1 ngày
-
Độ khó 4/5 3-5 ngày Mức phù hợp với người mới 52/100
OpenMathLib/OpenBLAS#6102 ·
Maintainer thường phản hồi trong vòng 1 ngày
Tất cả issue của OpenMathLib/OpenBLAS
Issue tương tự
-
Độ khó 1/5 Dưới một giờ Mức phù hợp với người mới 82/100
-
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 72/100
FStarLang/karamel#784 · 1 bình luận ·
Maintainer thường phản hồi trong vòng 1 ngày
-
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 70/100
DaveGamble/cJSON#1100 ·
-
UB: (int) cast of a user double outside int range in dispatch / vm_index_is_int / flat_index_atĐang mởarea:runtime-vm
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 72/100
InauguralSystems/EigenScript#1748 ·
Maintainer thường phản hồi trong vòng 1 ngày
-
bug
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 76/100
leanprover/lean4#15677 ·
Maintainer thường phản hồi trong vòng 1 ngày