^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1) // SPDX-License-Identifier: GPL-2.0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3) * Copyright (C) 2000 Hewlett-Packard Co
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4) * Copyright (C) 2000 David Mosberger-Tang <davidm@hpl.hp.com>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 6) * Generic IA-64 unwind info decoder.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 7) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 8) * This file is used both by the Linux kernel and objdump. Please keep
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 9) * the two copies of this file in sync.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 10) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 11) * You need to customize the decoder by defining the following
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 12) * macros/constants before including this file:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 13) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 14) * Types:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 15) * unw_word Unsigned integer type with at least 64 bits
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 16) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 17) * Register names:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 18) * UNW_REG_BSP
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 19) * UNW_REG_BSPSTORE
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 20) * UNW_REG_FPSR
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 21) * UNW_REG_LC
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 22) * UNW_REG_PFS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 23) * UNW_REG_PR
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 24) * UNW_REG_RNAT
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 25) * UNW_REG_PSP
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 26) * UNW_REG_RP
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 27) * UNW_REG_UNAT
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 28) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 29) * Decoder action macros:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 30) * UNW_DEC_BAD_CODE(code)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 31) * UNW_DEC_ABI(fmt,abi,context,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 32) * UNW_DEC_BR_GR(fmt,brmask,gr,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 33) * UNW_DEC_BR_MEM(fmt,brmask,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 34) * UNW_DEC_COPY_STATE(fmt,label,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 35) * UNW_DEC_EPILOGUE(fmt,t,ecount,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 36) * UNW_DEC_FRGR_MEM(fmt,grmask,frmask,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 37) * UNW_DEC_FR_MEM(fmt,frmask,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 38) * UNW_DEC_GR_GR(fmt,grmask,gr,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 39) * UNW_DEC_GR_MEM(fmt,grmask,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 40) * UNW_DEC_LABEL_STATE(fmt,label,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 41) * UNW_DEC_MEM_STACK_F(fmt,t,size,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 42) * UNW_DEC_MEM_STACK_V(fmt,t,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 43) * UNW_DEC_PRIUNAT_GR(fmt,r,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 44) * UNW_DEC_PRIUNAT_WHEN_GR(fmt,t,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 45) * UNW_DEC_PRIUNAT_WHEN_MEM(fmt,t,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 46) * UNW_DEC_PRIUNAT_WHEN_PSPREL(fmt,pspoff,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 47) * UNW_DEC_PRIUNAT_WHEN_SPREL(fmt,spoff,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 48) * UNW_DEC_PROLOGUE(fmt,body,rlen,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 49) * UNW_DEC_PROLOGUE_GR(fmt,rlen,mask,grsave,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 50) * UNW_DEC_REG_PSPREL(fmt,reg,pspoff,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 51) * UNW_DEC_REG_REG(fmt,src,dst,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 52) * UNW_DEC_REG_SPREL(fmt,reg,spoff,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 53) * UNW_DEC_REG_WHEN(fmt,reg,t,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 54) * UNW_DEC_RESTORE(fmt,t,abreg,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 55) * UNW_DEC_RESTORE_P(fmt,qp,t,abreg,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 56) * UNW_DEC_SPILL_BASE(fmt,pspoff,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 57) * UNW_DEC_SPILL_MASK(fmt,imaskp,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 58) * UNW_DEC_SPILL_PSPREL(fmt,t,abreg,pspoff,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 59) * UNW_DEC_SPILL_PSPREL_P(fmt,qp,t,abreg,pspoff,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 60) * UNW_DEC_SPILL_REG(fmt,t,abreg,x,ytreg,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 61) * UNW_DEC_SPILL_REG_P(fmt,qp,t,abreg,x,ytreg,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 62) * UNW_DEC_SPILL_SPREL(fmt,t,abreg,spoff,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 63) * UNW_DEC_SPILL_SPREL_P(fmt,qp,t,abreg,pspoff,arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 64) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 65)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 66) static unw_word
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 67) unw_decode_uleb128 (unsigned char **dpp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 68) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 69) unsigned shift = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 70) unw_word byte, result = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 71) unsigned char *bp = *dpp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 72)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 73) while (1)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 74) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 75) byte = *bp++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 76) result |= (byte & 0x7f) << shift;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 77) if ((byte & 0x80) == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 78) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 79) shift += 7;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 80) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 81) *dpp = bp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 82) return result;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 83) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 84)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 85) static unsigned char *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 86) unw_decode_x1 (unsigned char *dp, unsigned char code, void *arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 87) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 88) unsigned char byte1, abreg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 89) unw_word t, off;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 90)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 91) byte1 = *dp++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 92) t = unw_decode_uleb128 (&dp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 93) off = unw_decode_uleb128 (&dp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 94) abreg = (byte1 & 0x7f);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 95) if (byte1 & 0x80)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 96) UNW_DEC_SPILL_SPREL(X1, t, abreg, off, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 97) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 98) UNW_DEC_SPILL_PSPREL(X1, t, abreg, off, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 99) return dp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) static unsigned char *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) unw_decode_x2 (unsigned char *dp, unsigned char code, void *arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) unsigned char byte1, byte2, abreg, x, ytreg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) unw_word t;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) byte1 = *dp++; byte2 = *dp++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) t = unw_decode_uleb128 (&dp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) abreg = (byte1 & 0x7f);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) ytreg = byte2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) x = (byte1 >> 7) & 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) if ((byte1 & 0x80) == 0 && ytreg == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) UNW_DEC_RESTORE(X2, t, abreg, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) UNW_DEC_SPILL_REG(X2, t, abreg, x, ytreg, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) return dp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) static unsigned char *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) unw_decode_x3 (unsigned char *dp, unsigned char code, void *arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) unsigned char byte1, byte2, abreg, qp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) unw_word t, off;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) byte1 = *dp++; byte2 = *dp++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) t = unw_decode_uleb128 (&dp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) off = unw_decode_uleb128 (&dp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) qp = (byte1 & 0x3f);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) abreg = (byte2 & 0x7f);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) if (byte1 & 0x80)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134) UNW_DEC_SPILL_SPREL_P(X3, qp, t, abreg, off, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) UNW_DEC_SPILL_PSPREL_P(X3, qp, t, abreg, off, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) return dp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) static unsigned char *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) unw_decode_x4 (unsigned char *dp, unsigned char code, void *arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) unsigned char byte1, byte2, byte3, qp, abreg, x, ytreg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144) unw_word t;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) byte1 = *dp++; byte2 = *dp++; byte3 = *dp++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) t = unw_decode_uleb128 (&dp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149) qp = (byte1 & 0x3f);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) abreg = (byte2 & 0x7f);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) x = (byte2 >> 7) & 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) ytreg = byte3;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) if ((byte2 & 0x80) == 0 && byte3 == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) UNW_DEC_RESTORE_P(X4, qp, t, abreg, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157) UNW_DEC_SPILL_REG_P(X4, qp, t, abreg, x, ytreg, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) return dp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161) static unsigned char *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162) unw_decode_r1 (unsigned char *dp, unsigned char code, void *arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) int body = (code & 0x20) != 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165) unw_word rlen;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167) rlen = (code & 0x1f);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) UNW_DEC_PROLOGUE(R1, body, rlen, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) return dp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) static unsigned char *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) unw_decode_r2 (unsigned char *dp, unsigned char code, void *arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) unsigned char byte1, mask, grsave;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) unw_word rlen;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) byte1 = *dp++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) mask = ((code & 0x7) << 1) | ((byte1 >> 7) & 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181) grsave = (byte1 & 0x7f);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) rlen = unw_decode_uleb128 (&dp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) UNW_DEC_PROLOGUE_GR(R2, rlen, mask, grsave, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184) return dp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) static unsigned char *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188) unw_decode_r3 (unsigned char *dp, unsigned char code, void *arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) unw_word rlen;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192) rlen = unw_decode_uleb128 (&dp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) UNW_DEC_PROLOGUE(R3, ((code & 0x3) == 1), rlen, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) return dp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197) static unsigned char *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198) unw_decode_p1 (unsigned char *dp, unsigned char code, void *arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200) unsigned char brmask = (code & 0x1f);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202) UNW_DEC_BR_MEM(P1, brmask, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203) return dp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206) static unsigned char *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207) unw_decode_p2_p5 (unsigned char *dp, unsigned char code, void *arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) if ((code & 0x10) == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) unsigned char byte1 = *dp++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213) UNW_DEC_BR_GR(P2, ((code & 0xf) << 1) | ((byte1 >> 7) & 1),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214) (byte1 & 0x7f), arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216) else if ((code & 0x08) == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218) unsigned char byte1 = *dp++, r, dst;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220) r = ((code & 0x7) << 1) | ((byte1 >> 7) & 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221) dst = (byte1 & 0x7f);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222) switch (r)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224) case 0: UNW_DEC_REG_GR(P3, UNW_REG_PSP, dst, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225) case 1: UNW_DEC_REG_GR(P3, UNW_REG_RP, dst, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226) case 2: UNW_DEC_REG_GR(P3, UNW_REG_PFS, dst, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227) case 3: UNW_DEC_REG_GR(P3, UNW_REG_PR, dst, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228) case 4: UNW_DEC_REG_GR(P3, UNW_REG_UNAT, dst, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229) case 5: UNW_DEC_REG_GR(P3, UNW_REG_LC, dst, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230) case 6: UNW_DEC_RP_BR(P3, dst, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231) case 7: UNW_DEC_REG_GR(P3, UNW_REG_RNAT, dst, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232) case 8: UNW_DEC_REG_GR(P3, UNW_REG_BSP, dst, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233) case 9: UNW_DEC_REG_GR(P3, UNW_REG_BSPSTORE, dst, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234) case 10: UNW_DEC_REG_GR(P3, UNW_REG_FPSR, dst, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235) case 11: UNW_DEC_PRIUNAT_GR(P3, dst, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) default: UNW_DEC_BAD_CODE(r); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239) else if ((code & 0x7) == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) UNW_DEC_SPILL_MASK(P4, dp, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241) else if ((code & 0x7) == 1)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243) unw_word grmask, frmask, byte1, byte2, byte3;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) byte1 = *dp++; byte2 = *dp++; byte3 = *dp++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246) grmask = ((byte1 >> 4) & 0xf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247) frmask = ((byte1 & 0xf) << 16) | (byte2 << 8) | byte3;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248) UNW_DEC_FRGR_MEM(P5, grmask, frmask, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251) UNW_DEC_BAD_CODE(code);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252) return dp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255) static unsigned char *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) unw_decode_p6 (unsigned char *dp, unsigned char code, void *arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258) int gregs = (code & 0x10) != 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259) unsigned char mask = (code & 0x0f);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 260)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 261) if (gregs)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 262) UNW_DEC_GR_MEM(P6, mask, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 263) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 264) UNW_DEC_FR_MEM(P6, mask, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 265) return dp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 266) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 267)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 268) static unsigned char *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 269) unw_decode_p7_p10 (unsigned char *dp, unsigned char code, void *arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 270) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 271) unsigned char r, byte1, byte2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 272) unw_word t, size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 273)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 274) if ((code & 0x10) == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 275) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 276) r = (code & 0xf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 277) t = unw_decode_uleb128 (&dp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 278) switch (r)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 279) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 280) case 0:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 281) size = unw_decode_uleb128 (&dp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 282) UNW_DEC_MEM_STACK_F(P7, t, size, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 283) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 284)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 285) case 1: UNW_DEC_MEM_STACK_V(P7, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 286) case 2: UNW_DEC_SPILL_BASE(P7, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 287) case 3: UNW_DEC_REG_SPREL(P7, UNW_REG_PSP, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 288) case 4: UNW_DEC_REG_WHEN(P7, UNW_REG_RP, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 289) case 5: UNW_DEC_REG_PSPREL(P7, UNW_REG_RP, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 290) case 6: UNW_DEC_REG_WHEN(P7, UNW_REG_PFS, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 291) case 7: UNW_DEC_REG_PSPREL(P7, UNW_REG_PFS, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 292) case 8: UNW_DEC_REG_WHEN(P7, UNW_REG_PR, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 293) case 9: UNW_DEC_REG_PSPREL(P7, UNW_REG_PR, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 294) case 10: UNW_DEC_REG_WHEN(P7, UNW_REG_LC, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 295) case 11: UNW_DEC_REG_PSPREL(P7, UNW_REG_LC, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 296) case 12: UNW_DEC_REG_WHEN(P7, UNW_REG_UNAT, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 297) case 13: UNW_DEC_REG_PSPREL(P7, UNW_REG_UNAT, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 298) case 14: UNW_DEC_REG_WHEN(P7, UNW_REG_FPSR, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 299) case 15: UNW_DEC_REG_PSPREL(P7, UNW_REG_FPSR, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 300) default: UNW_DEC_BAD_CODE(r); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 301) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 302) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 303) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 304) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 305) switch (code & 0xf)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 306) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 307) case 0x0: /* p8 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 308) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 309) r = *dp++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 310) t = unw_decode_uleb128 (&dp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 311) switch (r)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 312) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 313) case 1: UNW_DEC_REG_SPREL(P8, UNW_REG_RP, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 314) case 2: UNW_DEC_REG_SPREL(P8, UNW_REG_PFS, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 315) case 3: UNW_DEC_REG_SPREL(P8, UNW_REG_PR, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 316) case 4: UNW_DEC_REG_SPREL(P8, UNW_REG_LC, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 317) case 5: UNW_DEC_REG_SPREL(P8, UNW_REG_UNAT, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 318) case 6: UNW_DEC_REG_SPREL(P8, UNW_REG_FPSR, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 319) case 7: UNW_DEC_REG_WHEN(P8, UNW_REG_BSP, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 320) case 8: UNW_DEC_REG_PSPREL(P8, UNW_REG_BSP, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 321) case 9: UNW_DEC_REG_SPREL(P8, UNW_REG_BSP, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 322) case 10: UNW_DEC_REG_WHEN(P8, UNW_REG_BSPSTORE, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 323) case 11: UNW_DEC_REG_PSPREL(P8, UNW_REG_BSPSTORE, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 324) case 12: UNW_DEC_REG_SPREL(P8, UNW_REG_BSPSTORE, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 325) case 13: UNW_DEC_REG_WHEN(P8, UNW_REG_RNAT, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 326) case 14: UNW_DEC_REG_PSPREL(P8, UNW_REG_RNAT, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 327) case 15: UNW_DEC_REG_SPREL(P8, UNW_REG_RNAT, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 328) case 16: UNW_DEC_PRIUNAT_WHEN_GR(P8, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 329) case 17: UNW_DEC_PRIUNAT_PSPREL(P8, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 330) case 18: UNW_DEC_PRIUNAT_SPREL(P8, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 331) case 19: UNW_DEC_PRIUNAT_WHEN_MEM(P8, t, arg); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 332) default: UNW_DEC_BAD_CODE(r); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 333) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 334) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 335) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 336)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 337) case 0x1:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 338) byte1 = *dp++; byte2 = *dp++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 339) UNW_DEC_GR_GR(P9, (byte1 & 0xf), (byte2 & 0x7f), arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 340) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 341)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 342) case 0xf: /* p10 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 343) byte1 = *dp++; byte2 = *dp++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 344) UNW_DEC_ABI(P10, byte1, byte2, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 345) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 346)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 347) case 0x9:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 348) return unw_decode_x1 (dp, code, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 349)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 350) case 0xa:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 351) return unw_decode_x2 (dp, code, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 352)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 353) case 0xb:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 354) return unw_decode_x3 (dp, code, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 355)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 356) case 0xc:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 357) return unw_decode_x4 (dp, code, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 358)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 359) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 360) UNW_DEC_BAD_CODE(code);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 361) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 362) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 363) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 364) return dp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 365) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 366)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 367) static unsigned char *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 368) unw_decode_b1 (unsigned char *dp, unsigned char code, void *arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 369) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 370) unw_word label = (code & 0x1f);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 371)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 372) if ((code & 0x20) != 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 373) UNW_DEC_COPY_STATE(B1, label, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 374) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 375) UNW_DEC_LABEL_STATE(B1, label, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 376) return dp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 377) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 378)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 379) static unsigned char *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 380) unw_decode_b2 (unsigned char *dp, unsigned char code, void *arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 381) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 382) unw_word t;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 383)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 384) t = unw_decode_uleb128 (&dp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 385) UNW_DEC_EPILOGUE(B2, t, (code & 0x1f), arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 386) return dp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 387) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 388)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 389) static unsigned char *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 390) unw_decode_b3_x4 (unsigned char *dp, unsigned char code, void *arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 391) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 392) unw_word t, ecount, label;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 393)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 394) if ((code & 0x10) == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 395) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 396) t = unw_decode_uleb128 (&dp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 397) ecount = unw_decode_uleb128 (&dp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 398) UNW_DEC_EPILOGUE(B3, t, ecount, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 399) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 400) else if ((code & 0x07) == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 401) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 402) label = unw_decode_uleb128 (&dp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 403) if ((code & 0x08) != 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 404) UNW_DEC_COPY_STATE(B4, label, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 405) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 406) UNW_DEC_LABEL_STATE(B4, label, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 407) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 408) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 409) switch (code & 0x7)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 410) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 411) case 1: return unw_decode_x1 (dp, code, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 412) case 2: return unw_decode_x2 (dp, code, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 413) case 3: return unw_decode_x3 (dp, code, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 414) case 4: return unw_decode_x4 (dp, code, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 415) default: UNW_DEC_BAD_CODE(code); break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 416) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 417) return dp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 418) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 419)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 420) typedef unsigned char *(*unw_decoder) (unsigned char *, unsigned char, void *);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 421)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 422) static unw_decoder unw_decode_table[2][8] =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 423) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 424) /* prologue table: */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 425) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 426) unw_decode_r1, /* 0 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 427) unw_decode_r1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 428) unw_decode_r2,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 429) unw_decode_r3,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 430) unw_decode_p1, /* 4 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 431) unw_decode_p2_p5,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 432) unw_decode_p6,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 433) unw_decode_p7_p10
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 434) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 435) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 436) unw_decode_r1, /* 0 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 437) unw_decode_r1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 438) unw_decode_r2,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 439) unw_decode_r3,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 440) unw_decode_b1, /* 4 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 441) unw_decode_b1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 442) unw_decode_b2,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 443) unw_decode_b3_x4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 444) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 445) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 446)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 447) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 448) * Decode one descriptor and return address of next descriptor.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 449) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 450) static inline unsigned char *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 451) unw_decode (unsigned char *dp, int inside_body, void *arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 452) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 453) unw_decoder decoder;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 454) unsigned char code;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 455)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 456) code = *dp++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 457) decoder = unw_decode_table[inside_body][code >> 5];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 458) dp = (*decoder) (dp, code, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 459) return dp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 460) }