1 /* 2 * Copyright (c) 2003, 2013, Oracle and/or its affiliates. All rights reserved. 3 * Copyright (c) 2015, Red Hat Inc. 4 * Copyright (c) 2021, Huawei Technologies Co., Ltd. All rights reserved. 5 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 6 * 7 * This code is free software; you can redistribute it and/or modify it 8 * under the terms of the GNU General Public License version 2 only, as 9 * published by the Free Software Foundation. 10 * 11 * This code is distributed in the hope that it will be useful, but WITHOUT 12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 14 * version 2 for more details (a copy is included in the LICENSE file that 15 * accompanied this code). 16 * 17 * You should have received a copy of the GNU General Public License version 18 * 2 along with this work; if not, write to the Free Software Foundation, 19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 20 * 21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 22 * or visit www.oracle.com if you need additional information or have any 23 * questions. 24 * 25 */ 26 27 package sun.jvm.hotspot.debugger.linux.riscv64; 28 29 import sun.jvm.hotspot.debugger.*; 30 import sun.jvm.hotspot.debugger.riscv64.*; 31 import sun.jvm.hotspot.debugger.linux.*; 32 import sun.jvm.hotspot.debugger.cdbg.*; 33 import sun.jvm.hotspot.debugger.cdbg.basic.*; 34 35 public final class LinuxRISCV64CFrame extends BasicCFrame { 36 private static final int C_FRAME_LINK_OFFSET = -2; 37 private static final int C_FRAME_RETURN_ADDR_OFFSET = -1; 38 39 public LinuxRISCV64CFrame(LinuxDebugger dbg, Address fp, Address pc) { 40 super(dbg.getCDebugger()); 41 this.fp = fp; 42 this.pc = pc; 43 this.dbg = dbg; 44 } 45 46 // override base class impl to avoid ELF parsing 47 public ClosestSymbol closestSymbolToPC() { 48 // try native lookup in debugger. 49 return dbg.lookup(dbg.getAddressValue(pc())); 50 } 51 52 public Address pc() { 53 return pc; 54 } 55 56 public Address localVariableBase() { 57 return fp; 58 } 59 60 public CFrame sender(ThreadProxy thread) { 61 RISCV64ThreadContext context = (RISCV64ThreadContext) thread.getContext(); 62 Address rsp = context.getRegisterAsAddress(RISCV64ThreadContext.SP); 63 64 if ((fp == null) || fp.lessThan(rsp)) { 65 return null; 66 } 67 68 // Check alignment of fp 69 if (dbg.getAddressValue(fp) % (2 * ADDRESS_SIZE) != 0) { 70 return null; 71 } 72 73 Address nextFP = fp.getAddressAt(C_FRAME_LINK_OFFSET * ADDRESS_SIZE); 74 if (nextFP == null || nextFP.lessThanOrEqual(fp)) { 75 return null; 76 } 77 Address nextPC = fp.getAddressAt(C_FRAME_RETURN_ADDR_OFFSET * ADDRESS_SIZE); 78 if (nextPC == null) { 79 return null; 80 } 81 return new LinuxRISCV64CFrame(dbg, nextFP, nextPC); 82 } 83 84 // package/class internals only 85 private static final int ADDRESS_SIZE = 8; 86 private Address pc; 87 private Address sp; 88 private Address fp; 89 private LinuxDebugger dbg; 90 }