diff --git a/clang/lib/Sema/SemaExpr.cpp b/clang/lib/Sema/SemaExpr.cpp --- a/clang/lib/Sema/SemaExpr.cpp +++ b/clang/lib/Sema/SemaExpr.cpp @@ -10528,7 +10528,11 @@ if (LHS.get()->getType()->isConstantMatrixType() || RHS.get()->getType()->isConstantMatrixType()) { - return CheckMatrixElementwiseOperands(LHS, RHS, Loc, CompLHSTy); + QualType compType = + CheckMatrixElementwiseOperands(LHS, RHS, Loc, CompLHSTy); + if (CompLHSTy) + *CompLHSTy = compType; + return compType; } QualType compType = UsualArithmeticConversions( @@ -10628,7 +10632,11 @@ if (LHS.get()->getType()->isConstantMatrixType() || RHS.get()->getType()->isConstantMatrixType()) { - return CheckMatrixElementwiseOperands(LHS, RHS, Loc, CompLHSTy); + QualType compType = + CheckMatrixElementwiseOperands(LHS, RHS, Loc, CompLHSTy); + if (CompLHSTy) + *CompLHSTy = compType; + return compType; } QualType compType = UsualArithmeticConversions( diff --git a/clang/test/CodeGen/matrix-type-operators.c b/clang/test/CodeGen/matrix-type-operators.c --- a/clang/test/CodeGen/matrix-type-operators.c +++ b/clang/test/CodeGen/matrix-type-operators.c @@ -17,6 +17,26 @@ a = b + c; } +void add_compound_assign_matrix_double(dx5x5_t a, dx5x5_t b) { + // CHECK-LABEL: define{{.*}} void @add_compound_assign_matrix_double(<25 x double> %a, <25 x double> %b) + // CHECK: [[B:%.*]] = load <25 x double>, <25 x double>* {{.*}}, align 8 + // CHECK-NEXT: [[A:%.*]] = load <25 x double>, <25 x double>* {{.*}}, align 8 + // CHECK-NEXT: [[RES:%.*]] = fadd <25 x double> [[A]], [[B]] + // CHECK-NEXT: store <25 x double> [[RES]], <25 x double>* {{.*}}, align 8 + + a += b; +} + +void subtract_compound_assign_matrix_double(dx5x5_t a, dx5x5_t b) { + // CHECK-LABEL: define{{.*}} void @subtract_compound_assign_matrix_double(<25 x double> %a, <25 x double> %b) + // CHECK: [[B:%.*]] = load <25 x double>, <25 x double>* {{.*}}, align 8 + // CHECK-NEXT: [[A:%.*]] = load <25 x double>, <25 x double>* {{.*}}, align 8 + // CHECK-NEXT: [[RES:%.*]] = fsub <25 x double> [[A]], [[B]] + // CHECK-NEXT: store <25 x double> [[RES]], <25 x double>* {{.*}}, align 8 + + a -= b; +} + void add_matrix_matrix_float(fx2x3_t a, fx2x3_t b, fx2x3_t c) { // CHECK-LABEL: define{{.*}} void @add_matrix_matrix_float(<6 x float> %a, <6 x float> %b, <6 x float> %c) // CHECK: [[B:%.*]] = load <6 x float>, <6 x float>* {{.*}}, align 4 @@ -27,6 +47,26 @@ a = b + c; } +void add_compound_assign_matrix_float(fx2x3_t a, fx2x3_t b) { + // CHECK-LABEL: define{{.*}} void @add_compound_assign_matrix_float(<6 x float> %a, <6 x float> %b) + // CHECK: [[B:%.*]] = load <6 x float>, <6 x float>* {{.*}}, align 4 + // CHECK-NEXT: [[A:%.*]] = load <6 x float>, <6 x float>* {{.*}}, align 4 + // CHECK-NEXT: [[RES:%.*]] = fadd <6 x float> [[A]], [[B]] + // CHECK-NEXT: store <6 x float> [[RES]], <6 x float>* {{.*}}, align 4 + + a += b; +} + +void subtract_compound_assign_matrix_float(fx2x3_t a, fx2x3_t b) { + // CHECK-LABEL: define{{.*}} void @subtract_compound_assign_matrix_float(<6 x float> %a, <6 x float> %b) + // CHECK: [[B:%.*]] = load <6 x float>, <6 x float>* {{.*}}, align 4 + // CHECK-NEXT: [[A:%.*]] = load <6 x float>, <6 x float>* {{.*}}, align 4 + // CHECK-NEXT: [[RES:%.*]] = fsub <6 x float> [[A]], [[B]] + // CHECK-NEXT: store <6 x float> [[RES]], <6 x float>* {{.*}}, align 4 + + a -= b; +} + void add_matrix_scalar_double_float(dx5x5_t a, float vf) { // CHECK-LABEL: define{{.*}} void @add_matrix_scalar_double_float(<25 x double> %a, float %vf) // CHECK: [[MATRIX:%.*]] = load <25 x double>, <25 x double>* {{.*}}, align 8 @@ -40,6 +80,32 @@ a = a + vf; } +void add_compound_matrix_scalar_double_float(dx5x5_t a, float vf) { + // CHECK-LABEL: define{{.*}} void @add_compound_matrix_scalar_double_float(<25 x double> %a, float %vf) + // CHECK: [[SCALAR:%.*]] = load float, float* %vf.addr, align 4 + // CHECK-NEXT: [[SCALAR_EXT:%.*]] = fpext float [[SCALAR]] to double + // CHECK-NEXT: [[MATRIX:%.*]] = load <25 x double>, <25 x double>* {{.*}}, align 8 + // CHECK-NEXT: [[SCALAR_EMBED:%.*]] = insertelement <25 x double> poison, double [[SCALAR_EXT]], i32 0 + // CHECK-NEXT: [[SCALAR_EMBED1:%.*]] = shufflevector <25 x double> [[SCALAR_EMBED]], <25 x double> poison, <25 x i32> zeroinitializer + // CHECK-NEXT: [[RES:%.*]] = fadd <25 x double> [[MATRIX]], [[SCALAR_EMBED1]] + // CHECK-NEXT: store <25 x double> [[RES]], <25 x double>* {{.*}}, align 8 + + a += vf; +} + +void subtract_compound_matrix_scalar_double_float(dx5x5_t a, float vf) { + // CHECK-LABEL: define{{.*}} void @subtract_compound_matrix_scalar_double_float(<25 x double> %a, float %vf) + // CHECK: [[SCALAR:%.*]] = load float, float* %vf.addr, align 4 + // CHECK-NEXT: [[SCALAR_EXT:%.*]] = fpext float [[SCALAR]] to double + // CHECK-NEXT: [[MATRIX:%.*]] = load <25 x double>, <25 x double>* {{.*}}, align 8 + // CHECK-NEXT: [[SCALAR_EMBED:%.*]] = insertelement <25 x double> poison, double [[SCALAR_EXT]], i32 0 + // CHECK-NEXT: [[SCALAR_EMBED1:%.*]] = shufflevector <25 x double> [[SCALAR_EMBED]], <25 x double> poison, <25 x i32> zeroinitializer + // CHECK-NEXT: [[RES:%.*]] = fsub <25 x double> [[MATRIX]], [[SCALAR_EMBED1]] + // CHECK-NEXT: store <25 x double> [[RES]], <25 x double>* {{.*}}, align 8 + + a -= vf; +} + void add_matrix_scalar_double_double(dx5x5_t a, double vd) { // CHECK-LABEL: define{{.*}} void @add_matrix_scalar_double_double(<25 x double> %a, double %vd) // CHECK: [[MATRIX:%.*]] = load <25 x double>, <25 x double>* {{.*}}, align 8 @@ -52,6 +118,28 @@ a = a + vd; } +void add_compound_matrix_scalar_double_double(dx5x5_t a, double vd) { + // CHECK-LABEL: define{{.*}} void @add_compound_matrix_scalar_double_double(<25 x double> %a, double %vd) + // CHECK: [[SCALAR:%.*]] = load double, double* %vd.addr, align 8 + // CHECK-NEXT: [[MATRIX:%.*]] = load <25 x double>, <25 x double>* {{.*}}, align 8 + // CHECK-NEXT: [[SCALAR_EMBED:%.*]] = insertelement <25 x double> poison, double [[SCALAR]], i32 0 + // CHECK-NEXT: [[SCALAR_EMBED1:%.*]] = shufflevector <25 x double> [[SCALAR_EMBED]], <25 x double> poison, <25 x i32> zeroinitializer + // CHECK-NEXT: [[RES:%.*]] = fadd <25 x double> [[MATRIX]], [[SCALAR_EMBED1]] + // store <25 x double> [[RES]], <25 x double>* {{.*}}, align 8 + a += vd; +} + +void subtract_compound_matrix_scalar_double_double(dx5x5_t a, double vd) { + // CHECK-LABEL: define{{.*}} void @subtract_compound_matrix_scalar_double_double(<25 x double> %a, double %vd) + // CHECK: [[SCALAR:%.*]] = load double, double* %vd.addr, align 8 + // CHECK-NEXT: [[MATRIX:%.*]] = load <25 x double>, <25 x double>* {{.*}}, align 8 + // CHECK-NEXT: [[SCALAR_EMBED:%.*]] = insertelement <25 x double> poison, double [[SCALAR]], i32 0 + // CHECK-NEXT: [[SCALAR_EMBED1:%.*]] = shufflevector <25 x double> [[SCALAR_EMBED]], <25 x double> poison, <25 x i32> zeroinitializer + // CHECK-NEXT: [[RES:%.*]] = fsub <25 x double> [[MATRIX]], [[SCALAR_EMBED1]] + // store <25 x double> [[RES]], <25 x double>* {{.*}}, align 8 + a -= vd; +} + void add_matrix_scalar_float_float(fx2x3_t b, float vf) { // CHECK-LABEL: define{{.*}} void @add_matrix_scalar_float_float(<6 x float> %b, float %vf) // CHECK: [[MATRIX:%.*]] = load <6 x float>, <6 x float>* {{.*}}, align 4 @@ -64,6 +152,28 @@ b = b + vf; } +void add_compound_matrix_scalar_float_float(fx2x3_t b, float vf) { + // CHECK-LABEL: define{{.*}} void @add_compound_matrix_scalar_float_float(<6 x float> %b, float %vf) + // CHECK: [[SCALAR:%.*]] = load float, float* %vf.addr, align 4 + // CHECK-NEXT: [[MATRIX:%.*]] = load <6 x float>, <6 x float>* %0, align 4 + // CHECK-NEXT: [[SCALAR_EMBED:%.*]] = insertelement <6 x float> poison, float [[SCALAR]], i32 0 + // CHECK-NEXT: [[SCALAR_EMBED1:%.*]] = shufflevector <6 x float> [[SCALAR_EMBED]], <6 x float> poison, <6 x i32> zeroinitializer + // CHECK-NEXT: [[RES:%.*]] = fadd <6 x float> [[MATRIX]], [[SCALAR_EMBED1]] + // CHECK-NEXT: store <6 x float> [[RES]], <6 x float>* {{.*}}, align 4 + b += vf; +} + +void subtract_compound_matrix_scalar_float_float(fx2x3_t b, float vf) { + // CHECK-LABEL: define{{.*}} void @subtract_compound_matrix_scalar_float_float(<6 x float> %b, float %vf) + // CHECK: [[SCALAR:%.*]] = load float, float* %vf.addr, align 4 + // CHECK-NEXT: [[MATRIX:%.*]] = load <6 x float>, <6 x float>* %0, align 4 + // CHECK-NEXT: [[SCALAR_EMBED:%.*]] = insertelement <6 x float> poison, float [[SCALAR]], i32 0 + // CHECK-NEXT: [[SCALAR_EMBED1:%.*]] = shufflevector <6 x float> [[SCALAR_EMBED]], <6 x float> poison, <6 x i32> zeroinitializer + // CHECK-NEXT: [[RES:%.*]] = fsub <6 x float> [[MATRIX]], [[SCALAR_EMBED1]] + // CHECK-NEXT: store <6 x float> [[RES]], <6 x float>* {{.*}}, align 4 + b -= vf; +} + void add_matrix_scalar_float_double(fx2x3_t b, double vd) { // CHECK-LABEL: define{{.*}} void @add_matrix_scalar_float_double(<6 x float> %b, double %vd) // CHECK: [[MATRIX:%.*]] = load <6 x float>, <6 x float>* {{.*}}, align 4 @@ -77,6 +187,30 @@ b = b + vd; } +void add_compound_matrix_scalar_float_double(fx2x3_t b, double vd) { + // CHECK-LABEL: define{{.*}} void @add_compound_matrix_scalar_float_double(<6 x float> %b, double %vd) + // CHECK: [[SCALAR:%.*]] = load double, double* %vd.addr, align 8 + // CHECK-NEXT: [[SCALAR_TRUNC:%.*]] = fptrunc double [[SCALAR]] to float + // CHECK-NEXT: [[MATRIX:%.*]] = load <6 x float>, <6 x float>* {{.*}}, align 4 + // CHECK-NEXT: [[SCALAR_EMBED:%.*]] = insertelement <6 x float> poison, float [[SCALAR_TRUNC]], i32 0 + // CHECK-NEXT: [[SCALAR_EMBED1:%.*]] = shufflevector <6 x float> [[SCALAR_EMBED]], <6 x float> poison, <6 x i32> zeroinitializer + // CHECK-NEXT: [[RES:%.*]] = fadd <6 x float> [[MATRIX]], [[SCALAR_EMBED1]] + // CHECK-NEXT: store <6 x float> [[RES]], <6 x float>* {{.*}}, align 4 + b += vd; +} + +void subtract_compound_matrix_scalar_float_double(fx2x3_t b, double vd) { + // CHECK-LABEL: define{{.*}} void @subtract_compound_matrix_scalar_float_double(<6 x float> %b, double %vd) + // CHECK: [[SCALAR:%.*]] = load double, double* %vd.addr, align 8 + // CHECK-NEXT: [[SCALAR_TRUNC:%.*]] = fptrunc double [[SCALAR]] to float + // CHECK-NEXT: [[MATRIX:%.*]] = load <6 x float>, <6 x float>* {{.*}}, align 4 + // CHECK-NEXT: [[SCALAR_EMBED:%.*]] = insertelement <6 x float> poison, float [[SCALAR_TRUNC]], i32 0 + // CHECK-NEXT: [[SCALAR_EMBED1:%.*]] = shufflevector <6 x float> [[SCALAR_EMBED]], <6 x float> poison, <6 x i32> zeroinitializer + // CHECK-NEXT: [[RES:%.*]] = fsub <6 x float> [[MATRIX]], [[SCALAR_EMBED1]] + // CHECK-NEXT: store <6 x float> [[RES]], <6 x float>* {{.*}}, align 4 + b -= vd; +} + // Integer matrix/scalar additions void add_matrix_matrix_int(ix9x3_t a, ix9x3_t b, ix9x3_t c) { @@ -88,6 +222,24 @@ a = b + c; } +void add_compound_matrix_matrix_int(ix9x3_t a, ix9x3_t b) { + // CHECK-LABEL: define{{.*}} void @add_compound_matrix_matrix_int(<27 x i32> %a, <27 x i32> %b) + // CHECK: [[B:%.*]] = load <27 x i32>, <27 x i32>* {{.*}}, align 4 + // CHECK: [[A:%.*]] = load <27 x i32>, <27 x i32>* {{.*}}, align 4 + // CHECK: [[RES:%.*]] = add <27 x i32> [[A]], [[B]] + // CHECK: store <27 x i32> [[RES]], <27 x i32>* {{.*}}, align 4 + a += b; +} + +void subtract_compound_matrix_matrix_int(ix9x3_t a, ix9x3_t b) { + // CHECK-LABEL: define{{.*}} void @subtract_compound_matrix_matrix_int(<27 x i32> %a, <27 x i32> %b) + // CHECK: [[B:%.*]] = load <27 x i32>, <27 x i32>* {{.*}}, align 4 + // CHECK: [[A:%.*]] = load <27 x i32>, <27 x i32>* {{.*}}, align 4 + // CHECK: [[RES:%.*]] = sub <27 x i32> [[A]], [[B]] + // CHECK: store <27 x i32> [[RES]], <27 x i32>* {{.*}}, align 4 + a -= b; +} + void add_matrix_matrix_unsigned_long_long(ullx4x2_t a, ullx4x2_t b, ullx4x2_t c) { // CHECK-LABEL: define{{.*}} void @add_matrix_matrix_unsigned_long_long(<8 x i64> %a, <8 x i64> %b, <8 x i64> %c) // CHECK: [[B:%.*]] = load <8 x i64>, <8 x i64>* {{.*}}, align 8 @@ -98,6 +250,26 @@ a = b + c; } +void add_compound_matrix_matrix_unsigned_long_long(ullx4x2_t a, ullx4x2_t b) { + // CHECK-LABEL: define{{.*}} void @add_compound_matrix_matrix_unsigned_long_long(<8 x i64> %a, <8 x i64> %b) + // CHECK: [[B:%.*]] = load <8 x i64>, <8 x i64>* {{.*}}, align 8 + // CHECK-NEXT: [[A:%.*]] = load <8 x i64>, <8 x i64>* {{.*}}, align 8 + // CHECK-NEXT: [[RES:%.*]] = add <8 x i64> [[A]], [[B]] + // CHECK-NEXT: store <8 x i64> [[RES]], <8 x i64>* {{.*}}, align 8 + + a += b; +} + +void subtract_compound_matrix_matrix_unsigned_long_long(ullx4x2_t a, ullx4x2_t b) { + // CHECK-LABEL: define{{.*}} void @subtract_compound_matrix_matrix_unsigned_long_long(<8 x i64> %a, <8 x i64> %b) + // CHECK: [[B:%.*]] = load <8 x i64>, <8 x i64>* {{.*}}, align 8 + // CHECK-NEXT: [[A:%.*]] = load <8 x i64>, <8 x i64>* {{.*}}, align 8 + // CHECK-NEXT: [[RES:%.*]] = sub <8 x i64> [[A]], [[B]] + // CHECK-NEXT: store <8 x i64> [[RES]], <8 x i64>* {{.*}}, align 8 + + a -= b; +} + void add_matrix_scalar_int_short(ix9x3_t a, short vs) { // CHECK-LABEL: define{{.*}} void @add_matrix_scalar_int_short(<27 x i32> %a, i16 signext %vs) // CHECK: [[MATRIX:%.*]] = load <27 x i32>, <27 x i32>* [[MAT_ADDR:%.*]], align 4 @@ -111,6 +283,32 @@ a = a + vs; } +void add_compound_matrix_scalar_int_short(ix9x3_t a, short vs) { + // CHECK-LABEL: define{{.*}} void @add_compound_matrix_scalar_int_short(<27 x i32> %a, i16 signext %vs) + // CHECK: [[SCALAR:%.*]] = load i16, i16* %vs.addr, align 2 + // CHECK-NEXT: [[SCALAR_EXT:%.*]] = sext i16 [[SCALAR]] to i32 + // CHECK-NEXT: [[MATRIX:%.*]] = load <27 x i32>, <27 x i32>* %0, align 4 + // CHECK-NEXT: [[SCALAR_EMBED:%.*]] = insertelement <27 x i32> poison, i32 [[SCALAR_EXT:%.*]], i32 0 + // CHECK-NEXT: [[SCALAR_EMBED1:%.*]] = shufflevector <27 x i32> [[SCALAR_EMBED]], <27 x i32> poison, <27 x i32> zeroinitializer + // CHECK-NEXT: [[RES:%.*]] = add <27 x i32> [[MATRIX]], [[SCALAR_EMBED1]] + // CHECK-NEXT: store <27 x i32> [[RES]], <27 x i32>* [[MAT_ADDR]], align 4 + + a += vs; +} + +void subtract_compound_matrix_scalar_int_short(ix9x3_t a, short vs) { + // CHECK-LABEL: define{{.*}} void @subtract_compound_matrix_scalar_int_short(<27 x i32> %a, i16 signext %vs) + // CHECK: [[SCALAR:%.*]] = load i16, i16* %vs.addr, align 2 + // CHECK-NEXT: [[SCALAR_EXT:%.*]] = sext i16 [[SCALAR]] to i32 + // CHECK-NEXT: [[MATRIX:%.*]] = load <27 x i32>, <27 x i32>* %0, align 4 + // CHECK-NEXT: [[SCALAR_EMBED:%.*]] = insertelement <27 x i32> poison, i32 [[SCALAR_EXT:%.*]], i32 0 + // CHECK-NEXT: [[SCALAR_EMBED1:%.*]] = shufflevector <27 x i32> [[SCALAR_EMBED]], <27 x i32> poison, <27 x i32> zeroinitializer + // CHECK-NEXT: [[RES:%.*]] = sub <27 x i32> [[MATRIX]], [[SCALAR_EMBED1]] + // CHECK-NEXT: store <27 x i32> [[RES]], <27 x i32>* [[MAT_ADDR]], align 4 + + a -= vs; +} + void add_matrix_scalar_int_long_int(ix9x3_t a, long int vli) { // CHECK-LABEL: define{{.*}} void @add_matrix_scalar_int_long_int(<27 x i32> %a, i64 %vli) // CHECK: [[MATRIX:%.*]] = load <27 x i32>, <27 x i32>* [[MAT_ADDR:%.*]], align 4 @@ -124,6 +322,32 @@ a = a + vli; } +void add_compound_matrix_scalar_int_long_int(ix9x3_t a, long int vli) { + // CHECK-LABEL: define{{.*}} void @add_compound_matrix_scalar_int_long_int(<27 x i32> %a, i64 %vli) + // CHECK: [[SCALAR:%.*]] = load i64, i64* %vli.addr, align 8 + // CHECK-NEXT: [[SCALAR_TRUNC:%.*]] = trunc i64 %1 to i32 + // CHECK-NEXT: [[MATRIX:%.*]] = load <27 x i32>, <27 x i32>* %0, align 4 + // CHECK-NEXT: [[SCALAR_EMBED:%.*]] = insertelement <27 x i32> poison, i32 [[SCALAR_TRUNC]], i32 0 + // CHECK-NEXT: [[SCALAR_EMBED1:%.*]] = shufflevector <27 x i32> [[SCALAR_EMBED]], <27 x i32> poison, <27 x i32> zeroinitializer + // CHECK-NEXT: [[RES:%.*]] = add <27 x i32> [[MATRIX]], [[SCALAR_EMBED1]] + // CHECK-NEXT: store <27 x i32> [[RES]], <27 x i32>* [[MAT_ADDR]], align 4 + + a += vli; +} + +void subtract_compound_matrix_scalar_int_long_int(ix9x3_t a, long int vli) { + // CHECK-LABEL: define{{.*}} void @subtract_compound_matrix_scalar_int_long_int(<27 x i32> %a, i64 %vli) + // CHECK: [[SCALAR:%.*]] = load i64, i64* %vli.addr, align 8 + // CHECK-NEXT: [[SCALAR_TRUNC:%.*]] = trunc i64 %1 to i32 + // CHECK-NEXT: [[MATRIX:%.*]] = load <27 x i32>, <27 x i32>* %0, align 4 + // CHECK-NEXT: [[SCALAR_EMBED:%.*]] = insertelement <27 x i32> poison, i32 [[SCALAR_TRUNC]], i32 0 + // CHECK-NEXT: [[SCALAR_EMBED1:%.*]] = shufflevector <27 x i32> [[SCALAR_EMBED]], <27 x i32> poison, <27 x i32> zeroinitializer + // CHECK-NEXT: [[RES:%.*]] = sub <27 x i32> [[MATRIX]], [[SCALAR_EMBED1]] + // CHECK-NEXT: store <27 x i32> [[RES]], <27 x i32>* [[MAT_ADDR]], align 4 + + a -= vli; +} + void add_matrix_scalar_int_unsigned_long_long(ix9x3_t a, unsigned long long int vulli) { // CHECK-LABEL: define{{.*}} void @add_matrix_scalar_int_unsigned_long_long(<27 x i32> %a, i64 %vulli) // CHECK: [[MATRIX:%.*]] = load <27 x i32>, <27 x i32>* [[MAT_ADDR:%.*]], align 4 @@ -137,6 +361,32 @@ a = a + vulli; } +void add_compound_matrix_scalar_int_unsigned_long_long(ix9x3_t a, unsigned long long int vulli) { + // CHECK-LABEL: define{{.*}} void @add_compound_matrix_scalar_int_unsigned_long_long(<27 x i32> %a, i64 %vulli) + // CHECK: [[SCALAR:%.*]] = load i64, i64* %vulli.addr, align 8 + // CHECK-NEXT: [[SCALAR_TRUNC:%.*]] = trunc i64 [[SCALAR]] to i32 + // CHECK-NEXT: [[MATRIX:%.*]] = load <27 x i32>, <27 x i32>* [[MATRIX_ADDR:%.*]], align 4 + // CHECK-NEXT: [[SCALAR_EMBED:%.*]] = insertelement <27 x i32> poison, i32 [[SCALAR_TRUNC]], i32 0 + // CHECK-NEXT: [[SCALAR_EMBED1:%.*]] = shufflevector <27 x i32> [[SCALAR_EMBED]], <27 x i32> poison, <27 x i32> zeroinitializer + // CHECK-NEXT: [[RES:%.*]] = add <27 x i32> [[MATRIX]], [[SCALAR_EMBED1]] + // CHECK-NEXT: store <27 x i32> [[RES]], <27 x i32>* [[MAT_ADDR]], align 4 + + a += vulli; +} + +void subtract_compound_matrix_scalar_int_unsigned_long_long(ix9x3_t a, unsigned long long int vulli) { + // CHECK-LABEL: define{{.*}} void @subtract_compound_matrix_scalar_int_unsigned_long_long(<27 x i32> %a, i64 %vulli) + // CHECK: [[SCALAR:%.*]] = load i64, i64* %vulli.addr, align 8 + // CHECK-NEXT: [[SCALAR_TRUNC:%.*]] = trunc i64 [[SCALAR]] to i32 + // CHECK-NEXT: [[MATRIX:%.*]] = load <27 x i32>, <27 x i32>* [[MATRIX_ADDR:%.*]], align 4 + // CHECK-NEXT: [[SCALAR_EMBED:%.*]] = insertelement <27 x i32> poison, i32 [[SCALAR_TRUNC]], i32 0 + // CHECK-NEXT: [[SCALAR_EMBED1:%.*]] = shufflevector <27 x i32> [[SCALAR_EMBED]], <27 x i32> poison, <27 x i32> zeroinitializer + // CHECK-NEXT: [[RES:%.*]] = sub <27 x i32> [[MATRIX]], [[SCALAR_EMBED1]] + // CHECK-NEXT: store <27 x i32> [[RES]], <27 x i32>* [[MAT_ADDR]], align 4 + + a -= vulli; +} + void add_matrix_scalar_long_long_int_short(ullx4x2_t b, short vs) { // CHECK-LABEL: define{{.*}} void @add_matrix_scalar_long_long_int_short(<8 x i64> %b, i16 signext %vs) // CHECK: [[SCALAR:%.*]] = load i16, i16* %vs.addr, align 2 @@ -150,6 +400,32 @@ b = vs + b; } +void add_compound_matrix_scalar_long_long_int_short(ullx4x2_t b, short vs) { + // CHECK-LABEL: define{{.*}} void @add_compound_matrix_scalar_long_long_int_short(<8 x i64> %b, i16 signext %vs) + // CHECK: [[SCALAR:%.*]] = load i16, i16* %vs.addr, align 2 + // CHECK-NEXT: [[SCALAR_EXT:%.*]] = sext i16 [[SCALAR]] to i64 + // CHECK-NEXT: [[MATRIX:%.*]] = load <8 x i64>, <8 x i64>* %0, align 8 + // CHECK-NEXT: [[SCALAR_EMBED:%.*]] = insertelement <8 x i64> poison, i64 [[SCALAR_EXT]], i32 0 + // CHECK-NEXT: [[SCALAR_EMBED1:%.*]] = shufflevector <8 x i64> [[SCALAR_EMBED]], <8 x i64> poison, <8 x i32> zeroinitializer + // CHECK-NEXT: [[RES:%.*]] = add <8 x i64> [[MATRIX]], [[SCALAR_EMBED1]] + // CHECK-NEXT: store <8 x i64> [[RES]], <8 x i64>* {{.*}}, align 8 + + b += vs; +} + +void subtract_compound_matrix_scalar_long_long_int_short(ullx4x2_t b, short vs) { + // CHECK-LABEL: define{{.*}} void @subtract_compound_matrix_scalar_long_long_int_short(<8 x i64> %b, i16 signext %vs) + // CHECK: [[SCALAR:%.*]] = load i16, i16* %vs.addr, align 2 + // CHECK-NEXT: [[SCALAR_EXT:%.*]] = sext i16 [[SCALAR]] to i64 + // CHECK-NEXT: [[MATRIX:%.*]] = load <8 x i64>, <8 x i64>* %0, align 8 + // CHECK-NEXT: [[SCALAR_EMBED:%.*]] = insertelement <8 x i64> poison, i64 [[SCALAR_EXT]], i32 0 + // CHECK-NEXT: [[SCALAR_EMBED1:%.*]] = shufflevector <8 x i64> [[SCALAR_EMBED]], <8 x i64> poison, <8 x i32> zeroinitializer + // CHECK-NEXT: [[RES:%.*]] = sub <8 x i64> [[MATRIX]], [[SCALAR_EMBED1]] + // CHECK-NEXT: store <8 x i64> [[RES]], <8 x i64>* {{.*}}, align 8 + + b -= vs; +} + void add_matrix_scalar_long_long_int_int(ullx4x2_t b, long int vli) { // CHECK-LABEL: define{{.*}} void @add_matrix_scalar_long_long_int_int(<8 x i64> %b, i64 %vli) // CHECK: [[SCALAR:%.*]] = load i64, i64* %vli.addr, align 8 @@ -162,6 +438,30 @@ b = vli + b; } +void add_compound_matrix_scalar_long_long_int_int(ullx4x2_t b, long int vli) { + // CHECK-LABEL: define{{.*}} void @add_compound_matrix_scalar_long_long_int_int(<8 x i64> %b, i64 %vli) + // CHECK: [[SCALAR:%.*]] = load i64, i64* %vli.addr, align 8 + // CHECK-NEXT: [[MATRIX:%.*]] = load <8 x i64>, <8 x i64>* {{.*}}, align 8 + // CHECK-NEXT: [[SCALAR_EMBED:%.*]] = insertelement <8 x i64> poison, i64 [[SCALAR]], i32 0 + // CHECK-NEXT: [[SCALAR_EMBED1:%.*]] = shufflevector <8 x i64> [[SCALAR_EMBED]], <8 x i64> poison, <8 x i32> zeroinitializer + // CHECK-NEXT: [[RES:%.*]] = add <8 x i64> [[MATRIX]], [[SCALAR_EMBED1]] + // CHECK-NEXT: store <8 x i64> [[RES]], <8 x i64>* {{.*}}, align 8 + + b += vli; +} + +void subtract_compound_matrix_scalar_long_long_int_int(ullx4x2_t b, long int vli) { + // CHECK-LABEL: define{{.*}} void @subtract_compound_matrix_scalar_long_long_int_int(<8 x i64> %b, i64 %vli) + // CHECK: [[SCALAR:%.*]] = load i64, i64* %vli.addr, align 8 + // CHECK-NEXT: [[MATRIX:%.*]] = load <8 x i64>, <8 x i64>* {{.*}}, align 8 + // CHECK-NEXT: [[SCALAR_EMBED:%.*]] = insertelement <8 x i64> poison, i64 [[SCALAR]], i32 0 + // CHECK-NEXT: [[SCALAR_EMBED1:%.*]] = shufflevector <8 x i64> [[SCALAR_EMBED]], <8 x i64> poison, <8 x i32> zeroinitializer + // CHECK-NEXT: [[RES:%.*]] = sub <8 x i64> [[MATRIX]], [[SCALAR_EMBED1]] + // CHECK-NEXT: store <8 x i64> [[RES]], <8 x i64>* {{.*}}, align 8 + + b -= vli; +} + void add_matrix_scalar_long_long_int_unsigned_long_long(ullx4x2_t b, unsigned long long int vulli) { // CHECK-LABEL: define{{.*}} void @add_matrix_scalar_long_long_int_unsigned_long_long // CHECK: [[SCALAR:%.*]] = load i64, i64* %vulli.addr, align 8 @@ -173,6 +473,30 @@ b = vulli + b; } +void add_compound_matrix_scalar_long_long_int_unsigned_long_long(ullx4x2_t b, unsigned long long int vulli) { + // CHECK-LABEL: define{{.*}} void @add_compound_matrix_scalar_long_long_int_unsigned_long_long + // CHECK: [[SCALAR:%.*]] = load i64, i64* %vulli.addr, align 8 + // CHECK-NEXT: [[MATRIX:%.*]] = load <8 x i64>, <8 x i64>* %0, align 8 + // CHECK-NEXT: [[SCALAR_EMBED:%.*]] = insertelement <8 x i64> poison, i64 [[SCALAR]], i32 0 + // CHECK-NEXT: [[SCALAR_EMBED1:%.*]] = shufflevector <8 x i64> [[SCALAR_EMBED]], <8 x i64> poison, <8 x i32> zeroinitializer + // CHECK-NEXT: [[RES:%.*]] = add <8 x i64> [[MATRIX]], [[SCALAR_EMBED1]] + // CHECK-NEXT: store <8 x i64> [[RES]], <8 x i64>* {{.*}}, align 8 + + b += vulli; +} + +void subtract_compound_matrix_scalar_long_long_int_unsigned_long_long(ullx4x2_t b, unsigned long long int vulli) { + // CHECK-LABEL: define{{.*}} void @subtract_compound_matrix_scalar_long_long_int_unsigned_long_long + // CHECK: [[SCALAR:%.*]] = load i64, i64* %vulli.addr, align 8 + // CHECK-NEXT: [[MATRIX:%.*]] = load <8 x i64>, <8 x i64>* %0, align 8 + // CHECK-NEXT: [[SCALAR_EMBED:%.*]] = insertelement <8 x i64> poison, i64 [[SCALAR]], i32 0 + // CHECK-NEXT: [[SCALAR_EMBED1:%.*]] = shufflevector <8 x i64> [[SCALAR_EMBED]], <8 x i64> poison, <8 x i32> zeroinitializer + // CHECK-NEXT: [[RES:%.*]] = sub <8 x i64> [[MATRIX]], [[SCALAR_EMBED1]] + // CHECK-NEXT: store <8 x i64> [[RES]], <8 x i64>* {{.*}}, align 8 + + b -= vulli; +} + // Tests for matrix multiplication. void multiply_matrix_matrix_double(dx5x5_t b, dx5x5_t c) { @@ -189,6 +513,16 @@ a = b * c; } +void multiply_compound_matrix_matrix_double(dx5x5_t b, dx5x5_t c) { + // CHECK-LABEL: @multiply_compound_matrix_matrix_double( + // CHECK: [[C:%.*]] = load <25 x double>, <25 x double>* {{.*}}, align 8 + // CHECK-NEXT: [[B:%.*]] = load <25 x double>, <25 x double>* {{.*}}, align 8 + // CHECK-NEXT: [[RES:%.*]] = call <25 x double> @llvm.matrix.multiply.v25f64.v25f64.v25f64(<25 x double> [[B]], <25 x double> [[C]], i32 5, i32 5, i32 5) + // CHECK-NEXT: store <25 x double> [[RES]], <25 x double>* {{.*}}, align 8 + // CHECK-NEXT: ret void + b *= c; +} + typedef int ix3x9_t __attribute__((matrix_type(3, 9))); typedef int ix9x9_t __attribute__((matrix_type(9, 9))); // CHECK-LABEL: @multiply_matrix_matrix_int( @@ -218,6 +552,20 @@ a = a * s; } +// CHECK-LABEL: @multiply_compound_double_matrix_scalar_float +// CHECK: [[S:%.*]] = load float, float* %s.addr, align 4 +// CHECK-NEXT: [[S_EXT:%.*]] = fpext float [[S]] to double +// CHECK-NEXT: [[A:%.*]] = load <25 x double>, <25 x double>* {{.*}}, align 8 +// CHECK-NEXT: [[VECINSERT:%.*]] = insertelement <25 x double> poison, double [[S_EXT]], i32 0 +// CHECK-NEXT: [[VECSPLAT:%.*]] = shufflevector <25 x double> [[VECINSERT]], <25 x double> poison, <25 x i32> zeroinitializer +// CHECK-NEXT: [[RES:%.*]] = fmul <25 x double> [[A]], [[VECSPLAT]] +// CHECK-NEXT: store <25 x double> [[RES]], <25 x double>* {{.*}}, align 8 +// CHECK-NEXT: ret void +// +void multiply_compound_double_matrix_scalar_float(dx5x5_t a, float s) { + a *= s; +} + // CHECK-LABEL: @multiply_double_matrix_scalar_double( // CHECK: [[A:%.*]] = load <25 x double>, <25 x double>* {{.*}}, align 8 // CHECK-NEXT: [[S:%.*]] = load double, double* %s.addr, align 8 @@ -231,6 +579,18 @@ a = a * s; } +// CHECK-LABEL: @multiply_compound_double_matrix_scalar_double( +// CHECK: [[S:%.*]] = load double, double* %s.addr, align 8 +// CHECK-NEXT: [[A:%.*]] = load <25 x double>, <25 x double>* {{.*}}, align 8 +// CHECK-NEXT: [[VECINSERT:%.*]] = insertelement <25 x double> poison, double [[S]], i32 0 +// CHECK-NEXT: [[VECSPLAT:%.*]] = shufflevector <25 x double> [[VECINSERT]], <25 x double> poison, <25 x i32> zeroinitializer +// CHECK-NEXT: [[RES:%.*]] = fmul <25 x double> [[A]], [[VECSPLAT]] +// CHECK-NEXT: store <25 x double> [[RES]], <25 x double>* {{.*}}, align 8 +// CHECK-NEXT: ret void +void multiply_compound_double_matrix_scalar_double(dx5x5_t a, double s) { + a *= s; +} + // CHECK-LABEL: @multiply_float_matrix_scalar_double( // CHECK: [[S:%.*]] = load double, double* %s.addr, align 8 // CHECK-NEXT: [[S_TRUNC:%.*]] = fptrunc double [[S]] to float @@ -245,6 +605,19 @@ b = s * b; } +// CHECK-LABEL: @multiply_compound_float_matrix_scalar_double( +// CHECK: [[S:%.*]] = load double, double* %s.addr, align 8 +// CHECK-NEXT: [[S_TRUNC:%.*]] = fptrunc double [[S]] to float +// CHECK-NEXT: [[MAT:%.*]] = load <6 x float>, <6 x float>* [[MAT_ADDR:%.*]], align 4 +// CHECK-NEXT: [[VECINSERT:%.*]] = insertelement <6 x float> poison, float [[S_TRUNC]], i32 0 +// CHECK-NEXT: [[VECSPLAT:%.*]] = shufflevector <6 x float> [[VECINSERT]], <6 x float> poison, <6 x i32> zeroinitializer +// CHECK-NEXT: [[RES:%.*]] = fmul <6 x float> [[MAT]], [[VECSPLAT]] +// store <6 x float> %3, <6 x float>* %0, align 4 +// ret void +void multiply_compound_float_matrix_scalar_double(fx2x3_t b, double s) { + b *= s; +} + // CHECK-LABEL: @multiply_int_matrix_scalar_short( // CHECK: [[S:%.*]] = load i16, i16* %s.addr, align 2 // CHECK-NEXT: [[S_EXT:%.*]] = sext i16 [[S]] to i32 @@ -259,6 +632,20 @@ b = s * b; } +// CHECK-LABEL: @multiply_compound_int_matrix_scalar_short( +// CHECK: [[S:%.*]] = load i16, i16* %s.addr, align 2 +// CHECK-NEXT: [[S_EXT:%.*]] = sext i16 [[S]] to i32 +// CHECK-NEXT: [[MAT:%.*]] = load <27 x i32>, <27 x i32>* [[MAT_ADDR:%.*]], align 4 +// CHECK-NEXT: [[VECINSERT:%.*]] = insertelement <27 x i32> poison, i32 [[S_EXT]], i32 0 +// CHECK-NEXT: [[VECSPLAT:%.*]] = shufflevector <27 x i32> [[VECINSERT]], <27 x i32> poison, <27 x i32> zeroinitializer +// CHECK-NEXT: [[RES:%.*]] = mul <27 x i32> [[MAT]], [[VECSPLAT]] +// CHECK-NEXT: store <27 x i32> [[RES]], <27 x i32>* [[MAT_ADDR]], align 4 +// CHECK-NEXT: ret void +// +void multiply_compound_int_matrix_scalar_short(ix9x3_t b, short s) { + b *= s; +} + // CHECK-LABEL: @multiply_int_matrix_scalar_ull( // CHECK: [[MAT:%.*]] = load <27 x i32>, <27 x i32>* [[MAT_ADDR:%.*]], align 4 // CHECK-NEXT: [[S:%.*]] = load i64, i64* %s.addr, align 8 @@ -273,6 +660,20 @@ b = b * s; } +void multiply_compound_int_matrix_scalar_ull(ix9x3_t b, unsigned long long s) { + // CHECK-LABEL: @multiply_compound_int_matrix_scalar_ull( + // CHECK: [[S:%.*]] = load i64, i64* %s.addr, align 8 + // CHECK-NEXT: [[S_TRUNC:%.*]] = trunc i64 [[S]] to i32 + // CHECK-NEXT: [[MAT:%.*]] = load <27 x i32>, <27 x i32>* [[MAT_ADDR:%.*]], align 4 + // CHECK-NEXT: [[VECINSERT:%.*]] = insertelement <27 x i32> poison, i32 [[S_TRUNC]], i32 0 + // CHECK-NEXT: [[VECSPLAT:%.*]] = shufflevector <27 x i32> [[VECINSERT]], <27 x i32> poison, <27 x i32> zeroinitializer + // CHECK-NEXT: [[RES:%.*]] = mul <27 x i32> [[MAT]], [[VECSPLAT]] + // CHECK-NEXT: store <27 x i32> [[RES]], <27 x i32>* [[MAT_ADDR]], align 4 + // CHECK-NEXT: ret void + + b *= s; +} + // CHECK-LABEL: @multiply_float_matrix_constant( // CHECK-NEXT: entry: // CHECK-NEXT: [[A_ADDR:%.*]] = alloca [6 x float], align 4 @@ -287,6 +688,19 @@ a = a * 2.5; } +// CHECK-LABEL: @multiply_compound_float_matrix_constant( +// CHECK-NEXT: entry: +// CHECK-NEXT: [[A_ADDR:%.*]] = alloca [6 x float], align 4 +// CHECK-NEXT: [[MAT_ADDR:%.*]] = bitcast [6 x float]* [[A_ADDR]] to <6 x float>* +// CHECK-NEXT: store <6 x float> [[A:%.*]], <6 x float>* [[MAT_ADDR]], align 4 +// CHECK-NEXT: [[MAT:%.*]] = load <6 x float>, <6 x float>* [[MAT_ADDR]], align 4 +// CHECK-NEXT: [[RES:%.*]] = fmul <6 x float> [[MAT]], +// CHECK-NEXT: store <6 x float> [[RES]], <6 x float>* [[MAT_ADDR]], align 4 +// CHECK-NEXT: ret void +void multiply_compound_float_matrix_constant(fx2x3_t a) { + a *= 2.5; +} + // CHECK-LABEL: @multiply_int_matrix_constant( // CHECK-NEXT: entry: // CHECK-NEXT: [[A_ADDR:%.*]] = alloca [27 x i32], align 4 @@ -301,6 +715,20 @@ a = 5 * a; } +// CHECK-LABEL: @multiply_compound_int_matrix_constant( +// CHECK-NEXT: entry: +// CHECK-NEXT: [[A_ADDR:%.*]] = alloca [27 x i32], align 4 +// CHECK-NEXT: [[MAT_ADDR:%.*]] = bitcast [27 x i32]* [[A_ADDR]] to <27 x i32>* +// CHECK-NEXT: store <27 x i32> [[A:%.*]], <27 x i32>* [[MAT_ADDR]], align 4 +// CHECK-NEXT: [[MAT:%.*]] = load <27 x i32>, <27 x i32>* [[MAT_ADDR]], align 4 +// CHECK-NEXT: [[RES:%.*]] = mul <27 x i32> [[MAT]], +// CHECK-NEXT: store <27 x i32> [[RES]], <27 x i32>* [[MAT_ADDR]], align 4 +// CHECK-NEXT: ret void +// +void multiply_compound_int_matrix_constant(ix9x3_t a) { + a *= 5; +} + // Tests for the matrix type operators. typedef double dx5x5_t __attribute__((matrix_type(5, 5))); diff --git a/clang/test/Sema/matrix-type-operators.c b/clang/test/Sema/matrix-type-operators.c --- a/clang/test/Sema/matrix-type-operators.c +++ b/clang/test/Sema/matrix-type-operators.c @@ -8,6 +8,9 @@ a = b + c; // expected-error@-1 {{invalid operands to binary expression ('sx5x10_t' (aka 'float __attribute__((matrix_type(5, 10)))') and 'sx10x5_t' (aka 'float __attribute__((matrix_type(10, 5)))'))}} + b += c; + // expected-error@-1 {{invalid operands to binary expression ('sx5x10_t' (aka 'float __attribute__((matrix_type(5, 10)))') and 'sx10x5_t' (aka 'float __attribute__((matrix_type(10, 5)))'))}} + a = b + b; // expected-error {{assigning to 'sx10x10_t' (aka 'float __attribute__((matrix_type(10, 10)))') from incompatible type 'sx5x10_t' (aka 'float __attribute__((matrix_type(5, 10)))')}} a = 10 + b; @@ -16,12 +19,19 @@ a = b + &c; // expected-error@-1 {{invalid operands to binary expression ('sx5x10_t' (aka 'float __attribute__((matrix_type(5, 10)))') and 'sx10x5_t *' (aka 'float __attribute__((matrix_type(10, 5)))*'))}} // expected-error@-2 {{casting 'sx10x5_t *' (aka 'float __attribute__((matrix_type(10, 5)))*') to incompatible type 'float'}} + + b -= &c; + // expected-error@-1 {{invalid operands to binary expression ('sx5x10_t' (aka 'float __attribute__((matrix_type(5, 10)))') and 'sx10x5_t *' (aka 'float __attribute__((matrix_type(10, 5)))*'))}} + // expected-error@-2 {{casting 'sx10x5_t *' (aka 'float __attribute__((matrix_type(10, 5)))*') to incompatible type 'float'}} } void sub(sx10x10_t a, sx5x10_t b, sx10x5_t c) { a = b - c; // expected-error@-1 {{invalid operands to binary expression ('sx5x10_t' (aka 'float __attribute__((matrix_type(5, 10)))') and 'sx10x5_t' (aka 'float __attribute__((matrix_type(10, 5)))'))}} + b -= c; + // expected-error@-1 {{invalid operands to binary expression ('sx5x10_t' (aka 'float __attribute__((matrix_type(5, 10)))') and 'sx10x5_t' (aka 'float __attribute__((matrix_type(10, 5)))'))}} + a = b - b; // expected-error {{assigning to 'sx10x10_t' (aka 'float __attribute__((matrix_type(10, 10)))') from incompatible type 'sx5x10_t' (aka 'float __attribute__((matrix_type(5, 10)))')}} a = 10 - b; @@ -30,6 +40,10 @@ a = b - &c; // expected-error@-1 {{invalid operands to binary expression ('sx5x10_t' (aka 'float __attribute__((matrix_type(5, 10)))') and 'sx10x5_t *' (aka 'float __attribute__((matrix_type(10, 5)))*'))}} // expected-error@-2 {{casting 'sx10x5_t *' (aka 'float __attribute__((matrix_type(10, 5)))*') to incompatible type 'float'}} + + b -= &c; + // expected-error@-1 {{invalid operands to binary expression ('sx5x10_t' (aka 'float __attribute__((matrix_type(5, 10)))') and 'sx10x5_t *' (aka 'float __attribute__((matrix_type(10, 5)))*'))}} + // expected-error@-2 {{casting 'sx10x5_t *' (aka 'float __attribute__((matrix_type(10, 5)))*') to incompatible type 'float'}} } typedef int ix10x5_t __attribute__((matrix_type(10, 5))); @@ -39,12 +53,16 @@ // Check dimension mismatches. a = a * b; // expected-error@-1 {{invalid operands to binary expression ('sx10x10_t' (aka 'float __attribute__((matrix_type(10, 10)))') and 'sx5x10_t' (aka 'float __attribute__((matrix_type(5, 10)))'))}} + a *= b; + // expected-error@-1 {{invalid operands to binary expression ('sx10x10_t' (aka 'float __attribute__((matrix_type(10, 10)))') and 'sx5x10_t' (aka 'float __attribute__((matrix_type(5, 10)))'))}} b = a * a; // expected-error@-1 {{assigning to 'sx5x10_t' (aka 'float __attribute__((matrix_type(5, 10)))') from incompatible type 'float __attribute__((matrix_type(10, 10)))'}} // Check element type mismatches. a = b * c; // expected-error@-1 {{invalid operands to binary expression ('sx5x10_t' (aka 'float __attribute__((matrix_type(5, 10)))') and 'ix10x5_t' (aka 'int __attribute__((matrix_type(10, 5)))'))}} + b *= c; + // expected-error@-1 {{invalid operands to binary expression ('sx5x10_t' (aka 'float __attribute__((matrix_type(5, 10)))') and 'ix10x5_t' (aka 'int __attribute__((matrix_type(10, 5)))'))}} d = a * a; // expected-error@-1 {{assigning to 'ix10x10_t' (aka 'int __attribute__((matrix_type(10, 10)))') from incompatible type 'float __attribute__((matrix_type(10, 10)))'}} @@ -62,9 +80,15 @@ a = a * p; // expected-error@-1 {{casting 'char *' to incompatible type 'float'}} // expected-error@-2 {{invalid operands to binary expression ('sx10x10_t' (aka 'float __attribute__((matrix_type(10, 10)))') and 'char *')}} + a *= p; + // expected-error@-1 {{casting 'char *' to incompatible type 'float'}} + // expected-error@-2 {{invalid operands to binary expression ('sx10x10_t' (aka 'float __attribute__((matrix_type(10, 10)))') and 'char *')}} a = p * a; // expected-error@-1 {{casting 'char *' to incompatible type 'float'}} // expected-error@-2 {{invalid operands to binary expression ('char *' and 'sx10x10_t' (aka 'float __attribute__((matrix_type(10, 10)))'))}} + p *= a; + // expected-error@-1 {{casting 'char *' to incompatible type 'float'}} + // expected-error@-2 {{invalid operands to binary expression ('char *' and 'sx10x10_t' (aka 'float __attribute__((matrix_type(10, 10)))'))}} sf = a * sf; // expected-error@-1 {{assigning to 'float' from incompatible type 'sx10x10_t' (aka 'float __attribute__((matrix_type(10, 10)))')}}