This effectively breaks sysutils/ruby-openfact and thus sysutils/ruby-openvox,
i.e. I am unable to manage my new machine via Puppet.

jca confirmed the minimal reproducer below crashes on his machine (Mac?), too.
It should print "My pid=...".

        $ dmesg | grep -m1 -w -e BTI -e IBT -e PAC
        $ dmesg | grep -m1 -w BT # related?
        cpu0: 
TLBIOS+IRANGE,TS+AXFLAG,FHM,DP,SM4,SM3,SHA3,RDM,Atomic,CRC32,SHA2+SHA512,SHA1,AES+PMULL,XS,I8MM,DGH,BF16,SPECRES,SB,FRINTTS,LRCPC+LDAPUR,FCMA,JSCVT,DPB+DCCVADP,GPA3,APA3+EPAC2+FPAC+COMBINED,WFXT,ECV+CNTHCTL,ASID16,AFP,PAN+ATS1E1+EPAN,LO,HPDS,VH,HAFDBS,ECBHB,IDS,AT,CSV3,CSV2+SCXT,DIT,AMU,RASv1p1,SVE,AdvSIMD+HP,FP+HP,BT,SSBS+MSR,MTE

        # pkg_add ruby34-ffi
        $ ktrace -di ruby34 
/usr/local/lib/ruby/gems/3.4/gems/ffi-1.17.2/samples/getpid.rb
        [ big dump of loaded files ]
        Illegal instruction (core dumped)

        $ kdump | grep BTCFI
         88448 ruby34   PSIG  SIGILL caught handler=0x221c893fcc mask=0<> 
code=ILL_BTCFI addr=0x22b6114000 trapno=905969665

        $ egdb -q ruby34{,.core} -batch -ex bt
        [New process 567109]
        [New process 558154]
        Core was generated by `ruby34'.
        Program terminated with signal SIGILL, Illegal instruction.
        #0  thrkill () at /tmp/-:3

        warning: 3      /tmp/-: No such file or directory
        [Current thread is 1 (process 567109)]
        #0  thrkill () at /tmp/-:3
        #1  0x000000221c892528 in ruby_default_signal () from 
/usr/local/lib/libruby34.so
        #2  0x000000221c759ae0 [PAC] in rb_bug_for_fatal_signal () from 
/usr/local/lib/libruby34.so
        #3  0x000000221c89401c [PAC] in sigill () from 
/usr/local/lib/libruby34.so
        #4  <signal handler called>
        #5  0x00000022b6114000 in ?? ()
        #6  0x000000680038c740 in ?? ()
        Backtrace stopped: Cannot access memory at address 0x800000000000001a

Doing the same in C works, though, so it seems like a Ruby specific issue:

        $ cat ffi-getpid.c                                                      
                                                                                
      
        #include <err.h>
        #include <ffi.h>
        #include <stdio.h>
        #include <unistd.h> // pid_t getpid(void);

        int main() {
                ffi_cif cif;
                pid_t result = 0;
                ffi_type *arg_types[0];
                void *arg_values[0];

                ffi_prep_cif(&cif, FFI_DEFAULT_ABI, 0, &ffi_type_sint32, 
arg_types);
                ffi_call(&cif, FFI_FN(getpid), &result, arg_values);
                printf("%d\n", result);
                return 0;
        }

        $ cc -I/usr/local/include -L/usr/local/lib -lffi -o ffi-getpid{,.c}     
                       
        ms-r1$ ./ffi-getpid                                                     
                                                                                
           
        54242

Even with USE_NOBTCFI-aarch64=Yes in lang/ruby/3.4 (as well as devel/ruby-ffi
and devel/libffi for good measure) it still fails.

Does this ring a bell for anyone more knowledgable in arm64/BTI/PAC hackery?

Reply via email to