https://gcc.gnu.org/bugzilla/show_bug.cgi?id=120436

            Bug ID: 120436
           Summary: division-by-zero when calling some RVV intrinsics
                    without the V extension
           Product: gcc
           Version: 16.0
            Status: UNCONFIRMED
          Severity: normal
          Priority: P3
         Component: target
          Assignee: unassigned at gcc dot gnu.org
          Reporter: artemiy at synopsys dot com
  Target Milestone: ---

A code snippet such as this (reduced from pr110109-1.c):

#include "riscv_vector.h"

void __attribute__ ((noinline, noclone))
clean_subreg (int32_t *in, int32_t *out, size_t m)
{
  vint16m8_t v24, v8, v16;
  vint32m8_t result = __riscv_vle32_v_i32m8 (in, 32);
  vint32m1_t v0 = __riscv_vget_v_i32m8_i32m1 (result, 0);
}

causes the following ICE when compiled with -mabi=ilp32 -march=rv32im:

1.c: In function 'clean_subreg':
1.c:8:3: internal compiler error: Floating point exception
    8 |   vint32m1_t v0 = __riscv_vget_v_i32m8_i32m1 (result, 0);
      |   ^~~~~~~~~~
0x2ce7eaf internal_error(char const*, ...)
        /SCRATCH/art/src/gcc-next/gcc/diagnostic-global-context.cc:517
0x14ae9ff crash_signal
        /SCRATCH/art/src/gcc-next/gcc/toplev.cc:321
0x19d2665 poly_int<2u, long>::is_constant() const
        /SCRATCH/art/src/gcc-next/gcc/poly-int.h:560
0x19d2665 poly_int<2u, poly_result<long, long, poly_coeff_pair_traits<long,
long>::result_kind>::type> exact_div<2u, long, long>(poly_int<2u, long> const&,
poly_int<2u, long> const&)
        /SCRATCH/art/src/gcc-next/gcc/poly-int.h:2191
0x19d2665 riscv_vector::vget_def::check(riscv_vector::function_checker&) const
       
/SCRATCH/art/src/gcc-next/gcc/config/riscv/riscv-vector-builtins-shapes.cc:929
0x19ce4fc riscv_vector::function_checker::check()
       
/SCRATCH/art/src/gcc-next/gcc/config/riscv/riscv-vector-builtins.cc:4955
0x19ce4fc riscv_vector::check_builtin_call(unsigned long, vec<unsigned long,
va_heap, vl_ptr>, unsigned int, tree_node*, unsigned int, tree_node**)
       
/SCRATCH/art/src/gcc-next/gcc/config/riscv/riscv-vector-builtins.cc:5362
0xdcff74 build_function_call_vec(unsigned long, vec<unsigned long, va_heap,
vl_ptr>, tree_node*, vec<tree_node*, va_gc, vl_embed>*, vec<tree_node*, va_gc,
vl_embed>*, tree_node*)
        /SCRATCH/art/src/gcc-next/gcc/c/c-typeck.cc:3909

Since the V extension is disabled at the time of checking the call to
__riscv_vget_v_i32m8_i32m1 (), all vector modes turn into BLKmode due to the
logic in vector_type_mode () and there is a 0/0 division happening in exact_div
() called from vget_def::check ():

/* vget_def class.  */
struct vget_def : public misc_def
{
  bool check (function_checker &c) const override
  {
    poly_int64 outer_size = GET_MODE_SIZE (c.arg_mode (0));
    poly_int64 inner_size = GET_MODE_SIZE (c.ret_mode ());
    unsigned int nvecs = exact_div (outer_size, inner_size).to_constant ();
    return c.require_immediate (1, 0, nvecs - 1);
  }
};

It feels like there should be some logic preventing all of the ::check()
functions to run in absence of the required V extensions (and maybe calling
riscv_report_v_required () or the like), or at least an audit of the behavior
of RVV builtin checkers when compiling without V.

godbolt for convenience:
https://godbolt.org/z/5ahMK9cfG

gcc -v output:
Using built-in specs.
COLLECT_GCC=/SCRATCH/art/install/riscv-gnu-toolchain/bin/riscv32-unknown-elf-gcc
COLLECT_LTO_WRAPPER=/SCRATCH/art/install/riscv-gnu-toolchain/libexec/gcc/riscv32-unknown-elf/16.0.0/lto-wrapper
Target: riscv32-unknown-elf
Configured with: /SCRATCH/art/src/gcc/configure --target=riscv32-unknown-elf
--prefix=/SCRATCH/art/install/riscv-gnu-toolchain-next --disable-shared
--disable-threads --enable-languages=c,c++ --with-pkgversion=g20aae412f82
--with-system-zlib --enable-tls --with-newlib
--with-sysroot=/SCRATCH/art/install/riscv-gnu-toolchain-next/riscv32-unknown-elf
--with-native-system-header-dir=/include --disable-libmudflap --disable-libssp
--disable-libquadmath --disable-libgomp --disable-nls
--disable-tm-clone-registry --src=/SCRATCH/art/src/gcc-next --disable-multilib
--with-abi=ilp32 --with-arch=rv32ima --with-tune=rocket
--with-isa-spec=20191213 'CFLAGS_FOR_TARGET=-O0 -g3' 'CXXFLAGS_FOR_TARGET=-O0
-g3'
Thread model: single
Supported LTO compression algorithms: zlib zstd
gcc version 16.0.0 20250525 (experimental) (g20aae412f82)

Reply via email to