Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: GPL-2.0
0002 #include <errno.h>
0003 #include <string.h>
0004 #include "perf_regs.h"
0005 #include "event.h"
0006 
0007 int __weak arch_sdt_arg_parse_op(char *old_op __maybe_unused,
0008                  char **new_op __maybe_unused)
0009 {
0010     return SDT_ARG_SKIP;
0011 }
0012 
0013 uint64_t __weak arch__intr_reg_mask(void)
0014 {
0015     return PERF_REGS_MASK;
0016 }
0017 
0018 uint64_t __weak arch__user_reg_mask(void)
0019 {
0020     return PERF_REGS_MASK;
0021 }
0022 
0023 #ifdef HAVE_PERF_REGS_SUPPORT
0024 
0025 #define perf_event_arm_regs perf_event_arm64_regs
0026 #include "../../arch/arm64/include/uapi/asm/perf_regs.h"
0027 #undef perf_event_arm_regs
0028 
0029 #include "../../arch/arm/include/uapi/asm/perf_regs.h"
0030 #include "../../arch/csky/include/uapi/asm/perf_regs.h"
0031 #include "../../arch/mips/include/uapi/asm/perf_regs.h"
0032 #include "../../arch/powerpc/include/uapi/asm/perf_regs.h"
0033 #include "../../arch/riscv/include/uapi/asm/perf_regs.h"
0034 #include "../../arch/s390/include/uapi/asm/perf_regs.h"
0035 #include "../../arch/x86/include/uapi/asm/perf_regs.h"
0036 
0037 static const char *__perf_reg_name_arm64(int id)
0038 {
0039     switch (id) {
0040     case PERF_REG_ARM64_X0:
0041         return "x0";
0042     case PERF_REG_ARM64_X1:
0043         return "x1";
0044     case PERF_REG_ARM64_X2:
0045         return "x2";
0046     case PERF_REG_ARM64_X3:
0047         return "x3";
0048     case PERF_REG_ARM64_X4:
0049         return "x4";
0050     case PERF_REG_ARM64_X5:
0051         return "x5";
0052     case PERF_REG_ARM64_X6:
0053         return "x6";
0054     case PERF_REG_ARM64_X7:
0055         return "x7";
0056     case PERF_REG_ARM64_X8:
0057         return "x8";
0058     case PERF_REG_ARM64_X9:
0059         return "x9";
0060     case PERF_REG_ARM64_X10:
0061         return "x10";
0062     case PERF_REG_ARM64_X11:
0063         return "x11";
0064     case PERF_REG_ARM64_X12:
0065         return "x12";
0066     case PERF_REG_ARM64_X13:
0067         return "x13";
0068     case PERF_REG_ARM64_X14:
0069         return "x14";
0070     case PERF_REG_ARM64_X15:
0071         return "x15";
0072     case PERF_REG_ARM64_X16:
0073         return "x16";
0074     case PERF_REG_ARM64_X17:
0075         return "x17";
0076     case PERF_REG_ARM64_X18:
0077         return "x18";
0078     case PERF_REG_ARM64_X19:
0079         return "x19";
0080     case PERF_REG_ARM64_X20:
0081         return "x20";
0082     case PERF_REG_ARM64_X21:
0083         return "x21";
0084     case PERF_REG_ARM64_X22:
0085         return "x22";
0086     case PERF_REG_ARM64_X23:
0087         return "x23";
0088     case PERF_REG_ARM64_X24:
0089         return "x24";
0090     case PERF_REG_ARM64_X25:
0091         return "x25";
0092     case PERF_REG_ARM64_X26:
0093         return "x26";
0094     case PERF_REG_ARM64_X27:
0095         return "x27";
0096     case PERF_REG_ARM64_X28:
0097         return "x28";
0098     case PERF_REG_ARM64_X29:
0099         return "x29";
0100     case PERF_REG_ARM64_SP:
0101         return "sp";
0102     case PERF_REG_ARM64_LR:
0103         return "lr";
0104     case PERF_REG_ARM64_PC:
0105         return "pc";
0106     case PERF_REG_ARM64_VG:
0107         return "vg";
0108     default:
0109         return NULL;
0110     }
0111 
0112     return NULL;
0113 }
0114 
0115 static const char *__perf_reg_name_arm(int id)
0116 {
0117     switch (id) {
0118     case PERF_REG_ARM_R0:
0119         return "r0";
0120     case PERF_REG_ARM_R1:
0121         return "r1";
0122     case PERF_REG_ARM_R2:
0123         return "r2";
0124     case PERF_REG_ARM_R3:
0125         return "r3";
0126     case PERF_REG_ARM_R4:
0127         return "r4";
0128     case PERF_REG_ARM_R5:
0129         return "r5";
0130     case PERF_REG_ARM_R6:
0131         return "r6";
0132     case PERF_REG_ARM_R7:
0133         return "r7";
0134     case PERF_REG_ARM_R8:
0135         return "r8";
0136     case PERF_REG_ARM_R9:
0137         return "r9";
0138     case PERF_REG_ARM_R10:
0139         return "r10";
0140     case PERF_REG_ARM_FP:
0141         return "fp";
0142     case PERF_REG_ARM_IP:
0143         return "ip";
0144     case PERF_REG_ARM_SP:
0145         return "sp";
0146     case PERF_REG_ARM_LR:
0147         return "lr";
0148     case PERF_REG_ARM_PC:
0149         return "pc";
0150     default:
0151         return NULL;
0152     }
0153 
0154     return NULL;
0155 }
0156 
0157 static const char *__perf_reg_name_csky(int id)
0158 {
0159     switch (id) {
0160     case PERF_REG_CSKY_A0:
0161         return "a0";
0162     case PERF_REG_CSKY_A1:
0163         return "a1";
0164     case PERF_REG_CSKY_A2:
0165         return "a2";
0166     case PERF_REG_CSKY_A3:
0167         return "a3";
0168     case PERF_REG_CSKY_REGS0:
0169         return "regs0";
0170     case PERF_REG_CSKY_REGS1:
0171         return "regs1";
0172     case PERF_REG_CSKY_REGS2:
0173         return "regs2";
0174     case PERF_REG_CSKY_REGS3:
0175         return "regs3";
0176     case PERF_REG_CSKY_REGS4:
0177         return "regs4";
0178     case PERF_REG_CSKY_REGS5:
0179         return "regs5";
0180     case PERF_REG_CSKY_REGS6:
0181         return "regs6";
0182     case PERF_REG_CSKY_REGS7:
0183         return "regs7";
0184     case PERF_REG_CSKY_REGS8:
0185         return "regs8";
0186     case PERF_REG_CSKY_REGS9:
0187         return "regs9";
0188     case PERF_REG_CSKY_SP:
0189         return "sp";
0190     case PERF_REG_CSKY_LR:
0191         return "lr";
0192     case PERF_REG_CSKY_PC:
0193         return "pc";
0194 #if defined(__CSKYABIV2__)
0195     case PERF_REG_CSKY_EXREGS0:
0196         return "exregs0";
0197     case PERF_REG_CSKY_EXREGS1:
0198         return "exregs1";
0199     case PERF_REG_CSKY_EXREGS2:
0200         return "exregs2";
0201     case PERF_REG_CSKY_EXREGS3:
0202         return "exregs3";
0203     case PERF_REG_CSKY_EXREGS4:
0204         return "exregs4";
0205     case PERF_REG_CSKY_EXREGS5:
0206         return "exregs5";
0207     case PERF_REG_CSKY_EXREGS6:
0208         return "exregs6";
0209     case PERF_REG_CSKY_EXREGS7:
0210         return "exregs7";
0211     case PERF_REG_CSKY_EXREGS8:
0212         return "exregs8";
0213     case PERF_REG_CSKY_EXREGS9:
0214         return "exregs9";
0215     case PERF_REG_CSKY_EXREGS10:
0216         return "exregs10";
0217     case PERF_REG_CSKY_EXREGS11:
0218         return "exregs11";
0219     case PERF_REG_CSKY_EXREGS12:
0220         return "exregs12";
0221     case PERF_REG_CSKY_EXREGS13:
0222         return "exregs13";
0223     case PERF_REG_CSKY_EXREGS14:
0224         return "exregs14";
0225     case PERF_REG_CSKY_TLS:
0226         return "tls";
0227     case PERF_REG_CSKY_HI:
0228         return "hi";
0229     case PERF_REG_CSKY_LO:
0230         return "lo";
0231 #endif
0232     default:
0233         return NULL;
0234     }
0235 
0236     return NULL;
0237 }
0238 
0239 static const char *__perf_reg_name_mips(int id)
0240 {
0241     switch (id) {
0242     case PERF_REG_MIPS_PC:
0243         return "PC";
0244     case PERF_REG_MIPS_R1:
0245         return "$1";
0246     case PERF_REG_MIPS_R2:
0247         return "$2";
0248     case PERF_REG_MIPS_R3:
0249         return "$3";
0250     case PERF_REG_MIPS_R4:
0251         return "$4";
0252     case PERF_REG_MIPS_R5:
0253         return "$5";
0254     case PERF_REG_MIPS_R6:
0255         return "$6";
0256     case PERF_REG_MIPS_R7:
0257         return "$7";
0258     case PERF_REG_MIPS_R8:
0259         return "$8";
0260     case PERF_REG_MIPS_R9:
0261         return "$9";
0262     case PERF_REG_MIPS_R10:
0263         return "$10";
0264     case PERF_REG_MIPS_R11:
0265         return "$11";
0266     case PERF_REG_MIPS_R12:
0267         return "$12";
0268     case PERF_REG_MIPS_R13:
0269         return "$13";
0270     case PERF_REG_MIPS_R14:
0271         return "$14";
0272     case PERF_REG_MIPS_R15:
0273         return "$15";
0274     case PERF_REG_MIPS_R16:
0275         return "$16";
0276     case PERF_REG_MIPS_R17:
0277         return "$17";
0278     case PERF_REG_MIPS_R18:
0279         return "$18";
0280     case PERF_REG_MIPS_R19:
0281         return "$19";
0282     case PERF_REG_MIPS_R20:
0283         return "$20";
0284     case PERF_REG_MIPS_R21:
0285         return "$21";
0286     case PERF_REG_MIPS_R22:
0287         return "$22";
0288     case PERF_REG_MIPS_R23:
0289         return "$23";
0290     case PERF_REG_MIPS_R24:
0291         return "$24";
0292     case PERF_REG_MIPS_R25:
0293         return "$25";
0294     case PERF_REG_MIPS_R28:
0295         return "$28";
0296     case PERF_REG_MIPS_R29:
0297         return "$29";
0298     case PERF_REG_MIPS_R30:
0299         return "$30";
0300     case PERF_REG_MIPS_R31:
0301         return "$31";
0302     default:
0303         break;
0304     }
0305     return NULL;
0306 }
0307 
0308 static const char *__perf_reg_name_powerpc(int id)
0309 {
0310     switch (id) {
0311     case PERF_REG_POWERPC_R0:
0312         return "r0";
0313     case PERF_REG_POWERPC_R1:
0314         return "r1";
0315     case PERF_REG_POWERPC_R2:
0316         return "r2";
0317     case PERF_REG_POWERPC_R3:
0318         return "r3";
0319     case PERF_REG_POWERPC_R4:
0320         return "r4";
0321     case PERF_REG_POWERPC_R5:
0322         return "r5";
0323     case PERF_REG_POWERPC_R6:
0324         return "r6";
0325     case PERF_REG_POWERPC_R7:
0326         return "r7";
0327     case PERF_REG_POWERPC_R8:
0328         return "r8";
0329     case PERF_REG_POWERPC_R9:
0330         return "r9";
0331     case PERF_REG_POWERPC_R10:
0332         return "r10";
0333     case PERF_REG_POWERPC_R11:
0334         return "r11";
0335     case PERF_REG_POWERPC_R12:
0336         return "r12";
0337     case PERF_REG_POWERPC_R13:
0338         return "r13";
0339     case PERF_REG_POWERPC_R14:
0340         return "r14";
0341     case PERF_REG_POWERPC_R15:
0342         return "r15";
0343     case PERF_REG_POWERPC_R16:
0344         return "r16";
0345     case PERF_REG_POWERPC_R17:
0346         return "r17";
0347     case PERF_REG_POWERPC_R18:
0348         return "r18";
0349     case PERF_REG_POWERPC_R19:
0350         return "r19";
0351     case PERF_REG_POWERPC_R20:
0352         return "r20";
0353     case PERF_REG_POWERPC_R21:
0354         return "r21";
0355     case PERF_REG_POWERPC_R22:
0356         return "r22";
0357     case PERF_REG_POWERPC_R23:
0358         return "r23";
0359     case PERF_REG_POWERPC_R24:
0360         return "r24";
0361     case PERF_REG_POWERPC_R25:
0362         return "r25";
0363     case PERF_REG_POWERPC_R26:
0364         return "r26";
0365     case PERF_REG_POWERPC_R27:
0366         return "r27";
0367     case PERF_REG_POWERPC_R28:
0368         return "r28";
0369     case PERF_REG_POWERPC_R29:
0370         return "r29";
0371     case PERF_REG_POWERPC_R30:
0372         return "r30";
0373     case PERF_REG_POWERPC_R31:
0374         return "r31";
0375     case PERF_REG_POWERPC_NIP:
0376         return "nip";
0377     case PERF_REG_POWERPC_MSR:
0378         return "msr";
0379     case PERF_REG_POWERPC_ORIG_R3:
0380         return "orig_r3";
0381     case PERF_REG_POWERPC_CTR:
0382         return "ctr";
0383     case PERF_REG_POWERPC_LINK:
0384         return "link";
0385     case PERF_REG_POWERPC_XER:
0386         return "xer";
0387     case PERF_REG_POWERPC_CCR:
0388         return "ccr";
0389     case PERF_REG_POWERPC_SOFTE:
0390         return "softe";
0391     case PERF_REG_POWERPC_TRAP:
0392         return "trap";
0393     case PERF_REG_POWERPC_DAR:
0394         return "dar";
0395     case PERF_REG_POWERPC_DSISR:
0396         return "dsisr";
0397     case PERF_REG_POWERPC_SIER:
0398         return "sier";
0399     case PERF_REG_POWERPC_MMCRA:
0400         return "mmcra";
0401     case PERF_REG_POWERPC_MMCR0:
0402         return "mmcr0";
0403     case PERF_REG_POWERPC_MMCR1:
0404         return "mmcr1";
0405     case PERF_REG_POWERPC_MMCR2:
0406         return "mmcr2";
0407     case PERF_REG_POWERPC_MMCR3:
0408         return "mmcr3";
0409     case PERF_REG_POWERPC_SIER2:
0410         return "sier2";
0411     case PERF_REG_POWERPC_SIER3:
0412         return "sier3";
0413     case PERF_REG_POWERPC_PMC1:
0414         return "pmc1";
0415     case PERF_REG_POWERPC_PMC2:
0416         return "pmc2";
0417     case PERF_REG_POWERPC_PMC3:
0418         return "pmc3";
0419     case PERF_REG_POWERPC_PMC4:
0420         return "pmc4";
0421     case PERF_REG_POWERPC_PMC5:
0422         return "pmc5";
0423     case PERF_REG_POWERPC_PMC6:
0424         return "pmc6";
0425     case PERF_REG_POWERPC_SDAR:
0426         return "sdar";
0427     case PERF_REG_POWERPC_SIAR:
0428         return "siar";
0429     default:
0430         break;
0431     }
0432     return NULL;
0433 }
0434 
0435 static const char *__perf_reg_name_riscv(int id)
0436 {
0437     switch (id) {
0438     case PERF_REG_RISCV_PC:
0439         return "pc";
0440     case PERF_REG_RISCV_RA:
0441         return "ra";
0442     case PERF_REG_RISCV_SP:
0443         return "sp";
0444     case PERF_REG_RISCV_GP:
0445         return "gp";
0446     case PERF_REG_RISCV_TP:
0447         return "tp";
0448     case PERF_REG_RISCV_T0:
0449         return "t0";
0450     case PERF_REG_RISCV_T1:
0451         return "t1";
0452     case PERF_REG_RISCV_T2:
0453         return "t2";
0454     case PERF_REG_RISCV_S0:
0455         return "s0";
0456     case PERF_REG_RISCV_S1:
0457         return "s1";
0458     case PERF_REG_RISCV_A0:
0459         return "a0";
0460     case PERF_REG_RISCV_A1:
0461         return "a1";
0462     case PERF_REG_RISCV_A2:
0463         return "a2";
0464     case PERF_REG_RISCV_A3:
0465         return "a3";
0466     case PERF_REG_RISCV_A4:
0467         return "a4";
0468     case PERF_REG_RISCV_A5:
0469         return "a5";
0470     case PERF_REG_RISCV_A6:
0471         return "a6";
0472     case PERF_REG_RISCV_A7:
0473         return "a7";
0474     case PERF_REG_RISCV_S2:
0475         return "s2";
0476     case PERF_REG_RISCV_S3:
0477         return "s3";
0478     case PERF_REG_RISCV_S4:
0479         return "s4";
0480     case PERF_REG_RISCV_S5:
0481         return "s5";
0482     case PERF_REG_RISCV_S6:
0483         return "s6";
0484     case PERF_REG_RISCV_S7:
0485         return "s7";
0486     case PERF_REG_RISCV_S8:
0487         return "s8";
0488     case PERF_REG_RISCV_S9:
0489         return "s9";
0490     case PERF_REG_RISCV_S10:
0491         return "s10";
0492     case PERF_REG_RISCV_S11:
0493         return "s11";
0494     case PERF_REG_RISCV_T3:
0495         return "t3";
0496     case PERF_REG_RISCV_T4:
0497         return "t4";
0498     case PERF_REG_RISCV_T5:
0499         return "t5";
0500     case PERF_REG_RISCV_T6:
0501         return "t6";
0502     default:
0503         return NULL;
0504     }
0505 
0506     return NULL;
0507 }
0508 
0509 static const char *__perf_reg_name_s390(int id)
0510 {
0511     switch (id) {
0512     case PERF_REG_S390_R0:
0513         return "R0";
0514     case PERF_REG_S390_R1:
0515         return "R1";
0516     case PERF_REG_S390_R2:
0517         return "R2";
0518     case PERF_REG_S390_R3:
0519         return "R3";
0520     case PERF_REG_S390_R4:
0521         return "R4";
0522     case PERF_REG_S390_R5:
0523         return "R5";
0524     case PERF_REG_S390_R6:
0525         return "R6";
0526     case PERF_REG_S390_R7:
0527         return "R7";
0528     case PERF_REG_S390_R8:
0529         return "R8";
0530     case PERF_REG_S390_R9:
0531         return "R9";
0532     case PERF_REG_S390_R10:
0533         return "R10";
0534     case PERF_REG_S390_R11:
0535         return "R11";
0536     case PERF_REG_S390_R12:
0537         return "R12";
0538     case PERF_REG_S390_R13:
0539         return "R13";
0540     case PERF_REG_S390_R14:
0541         return "R14";
0542     case PERF_REG_S390_R15:
0543         return "R15";
0544     case PERF_REG_S390_FP0:
0545         return "FP0";
0546     case PERF_REG_S390_FP1:
0547         return "FP1";
0548     case PERF_REG_S390_FP2:
0549         return "FP2";
0550     case PERF_REG_S390_FP3:
0551         return "FP3";
0552     case PERF_REG_S390_FP4:
0553         return "FP4";
0554     case PERF_REG_S390_FP5:
0555         return "FP5";
0556     case PERF_REG_S390_FP6:
0557         return "FP6";
0558     case PERF_REG_S390_FP7:
0559         return "FP7";
0560     case PERF_REG_S390_FP8:
0561         return "FP8";
0562     case PERF_REG_S390_FP9:
0563         return "FP9";
0564     case PERF_REG_S390_FP10:
0565         return "FP10";
0566     case PERF_REG_S390_FP11:
0567         return "FP11";
0568     case PERF_REG_S390_FP12:
0569         return "FP12";
0570     case PERF_REG_S390_FP13:
0571         return "FP13";
0572     case PERF_REG_S390_FP14:
0573         return "FP14";
0574     case PERF_REG_S390_FP15:
0575         return "FP15";
0576     case PERF_REG_S390_MASK:
0577         return "MASK";
0578     case PERF_REG_S390_PC:
0579         return "PC";
0580     default:
0581         return NULL;
0582     }
0583 
0584     return NULL;
0585 }
0586 
0587 static const char *__perf_reg_name_x86(int id)
0588 {
0589     switch (id) {
0590     case PERF_REG_X86_AX:
0591         return "AX";
0592     case PERF_REG_X86_BX:
0593         return "BX";
0594     case PERF_REG_X86_CX:
0595         return "CX";
0596     case PERF_REG_X86_DX:
0597         return "DX";
0598     case PERF_REG_X86_SI:
0599         return "SI";
0600     case PERF_REG_X86_DI:
0601         return "DI";
0602     case PERF_REG_X86_BP:
0603         return "BP";
0604     case PERF_REG_X86_SP:
0605         return "SP";
0606     case PERF_REG_X86_IP:
0607         return "IP";
0608     case PERF_REG_X86_FLAGS:
0609         return "FLAGS";
0610     case PERF_REG_X86_CS:
0611         return "CS";
0612     case PERF_REG_X86_SS:
0613         return "SS";
0614     case PERF_REG_X86_DS:
0615         return "DS";
0616     case PERF_REG_X86_ES:
0617         return "ES";
0618     case PERF_REG_X86_FS:
0619         return "FS";
0620     case PERF_REG_X86_GS:
0621         return "GS";
0622     case PERF_REG_X86_R8:
0623         return "R8";
0624     case PERF_REG_X86_R9:
0625         return "R9";
0626     case PERF_REG_X86_R10:
0627         return "R10";
0628     case PERF_REG_X86_R11:
0629         return "R11";
0630     case PERF_REG_X86_R12:
0631         return "R12";
0632     case PERF_REG_X86_R13:
0633         return "R13";
0634     case PERF_REG_X86_R14:
0635         return "R14";
0636     case PERF_REG_X86_R15:
0637         return "R15";
0638 
0639 #define XMM(x) \
0640     case PERF_REG_X86_XMM ## x: \
0641     case PERF_REG_X86_XMM ## x + 1: \
0642         return "XMM" #x;
0643     XMM(0)
0644     XMM(1)
0645     XMM(2)
0646     XMM(3)
0647     XMM(4)
0648     XMM(5)
0649     XMM(6)
0650     XMM(7)
0651     XMM(8)
0652     XMM(9)
0653     XMM(10)
0654     XMM(11)
0655     XMM(12)
0656     XMM(13)
0657     XMM(14)
0658     XMM(15)
0659 #undef XMM
0660     default:
0661         return NULL;
0662     }
0663 
0664     return NULL;
0665 }
0666 
0667 const char *perf_reg_name(int id, const char *arch)
0668 {
0669     const char *reg_name = NULL;
0670 
0671     if (!strcmp(arch, "csky"))
0672         reg_name = __perf_reg_name_csky(id);
0673     else if (!strcmp(arch, "mips"))
0674         reg_name = __perf_reg_name_mips(id);
0675     else if (!strcmp(arch, "powerpc"))
0676         reg_name = __perf_reg_name_powerpc(id);
0677     else if (!strcmp(arch, "riscv"))
0678         reg_name = __perf_reg_name_riscv(id);
0679     else if (!strcmp(arch, "s390"))
0680         reg_name = __perf_reg_name_s390(id);
0681     else if (!strcmp(arch, "x86"))
0682         reg_name = __perf_reg_name_x86(id);
0683     else if (!strcmp(arch, "arm"))
0684         reg_name = __perf_reg_name_arm(id);
0685     else if (!strcmp(arch, "arm64"))
0686         reg_name = __perf_reg_name_arm64(id);
0687 
0688     return reg_name ?: "unknown";
0689 }
0690 
0691 int perf_reg_value(u64 *valp, struct regs_dump *regs, int id)
0692 {
0693     int i, idx = 0;
0694     u64 mask = regs->mask;
0695 
0696     if ((u64)id >= PERF_SAMPLE_REGS_CACHE_SIZE)
0697         return -EINVAL;
0698 
0699     if (regs->cache_mask & (1ULL << id))
0700         goto out;
0701 
0702     if (!(mask & (1ULL << id)))
0703         return -EINVAL;
0704 
0705     for (i = 0; i < id; i++) {
0706         if (mask & (1ULL << i))
0707             idx++;
0708     }
0709 
0710     regs->cache_mask |= (1ULL << id);
0711     regs->cache_regs[id] = regs->regs[idx];
0712 
0713 out:
0714     *valp = regs->cache_regs[id];
0715     return 0;
0716 }
0717 #endif