source: trunk/gcc/libjava/gnu/gcj/runtime/natNameFinder.cc

Last change on this file was 1389, checked in by bird, 21 years ago

Initial revision

  • Property cvs2svn:cvs-rev set to 1.1
  • Property svn:eol-style set to native
  • Property svn:executable set to *
File size: 4.2 KB
Line 
1// natNameFinder.cc - native helper methods for NameFinder.java
2
3/* Copyright (C) 2002 Free Software Foundation, Inc
4
5 This file is part of libgcj.
6
7This software is copyrighted work licensed under the terms of the
8Libgcj License. Please consult the file "LIBGCJ_LICENSE" for
9details. */
10
11/**
12 * @author Mark Wielaard (mark@klomp.org)
13 * Based on the old name-finder.cc by Andrew Haley <aph@cygnus.com>.
14 */
15
16#include <config.h>
17
18#include <string.h>
19
20#include <gcj/cni.h>
21#include <jvm.h>
22#include <java/lang/String.h>
23#include <java/lang/StackTraceElement.h>
24#include <java/lang/StringBuffer.h>
25#include <java-interp.h>
26
27#include <gnu/gcj/runtime/NameFinder.h>
28
29#ifdef HAVE_DLFCN_H
30#include <dlfcn.h>
31#endif
32
33// On some systems, a prefix is attached to a method name before
34// it is exported as a label. The GCC preprocessor predefines
35// this prefix as the macro __USER_LABEL_PREFIX__ which expands to
36// a string (not string constant) representing the prefix, if any.
37#undef LABEL_PREFIX
38#ifdef __USER_LABEL_PREFIX__
39
40#define USER_LABEL_PREFIX_STRING_0(s) #s
41#define USER_LABEL_PREFIX_STRING(s) USER_LABEL_PREFIX_STRING_0(s)
42
43#define LABEL_PREFIX USER_LABEL_PREFIX_STRING(__USER_LABEL_PREFIX__)
44
45#else /* __USER_LABEL_PREFIX__ */
46
47#define LABEL_PREFIX ""
48
49#endif /* ! __USER_LABEL_PREFIX__ */
50
51java::lang::String*
52gnu::gcj::runtime::NameFinder::getExternalLabel (java::lang::String* name)
53{
54 jsize nameLen = JvGetStringUTFLength (name);
55 jsize pfxLen = strlen (LABEL_PREFIX);
56 char *newName = (char *) JvMalloc (pfxLen + nameLen + 1);
57 *(newName + 0) = '\0';
58 strcpy (newName, LABEL_PREFIX);
59 JvGetStringUTFRegion (name, 0, nameLen, newName + pfxLen);
60 *(newName + pfxLen + nameLen) = '\0';
61 return JvNewStringLatin1 (newName);
62}
63
64java::lang::String*
65gnu::gcj::runtime::NameFinder::getExecutable (void)
66{
67 return JvNewStringLatin1 (_Jv_ThisExecutable ());
68}
69
70java::lang::String*
71gnu::gcj::runtime::NameFinder::getAddrAsString(RawData* addrs, jint n)
72{
73 _Jv_frame_info *p = (_Jv_frame_info *) addrs;
74 typedef unsigned word_t __attribute ((mode (word)));
75 word_t w = (word_t) p[n].addr;
76 int digits = sizeof (void *) * 2;
77 char hex[digits+5];
78
79 strcpy (hex, "0x");
80 for (int i = digits - 1; i >= 0; i--)
81 {
82 int digit = w % 16;
83
84 w /= 16;
85 hex[i+2] = digit > 9 ? 'a' + digit - 10 : '0' + digit;
86 }
87 hex [digits+2] = 0;
88
89 return JvNewStringLatin1(hex);
90}
91
92java::lang::StackTraceElement*
93gnu::gcj::runtime::NameFinder::dladdrLookup(RawData* addrs, jint n)
94{
95#if defined (HAVE_DLFCN_H) && defined (HAVE_DLADDR)
96 extern char **_Jv_argv;
97 char name[1024];
98 char file_name[1024];
99 _Jv_frame_info *stack = (_Jv_frame_info *) addrs;
100 void* p = stack[n].addr;
101 Dl_info dl_info;
102
103 if (dladdr (p, &dl_info))
104 {
105 if (dl_info.dli_fname)
106 strncpy (file_name, dl_info.dli_fname, sizeof file_name);
107 if (dl_info.dli_sname)
108 strncpy (name, dl_info.dli_sname, sizeof name);
109
110 /* Don't trust dladdr() if the address is from the main program. */
111 if (dl_info.dli_fname != NULL
112 && dl_info.dli_sname != NULL
113 && (_Jv_argv == NULL || strcmp (file_name, _Jv_argv[0]) != 0))
114 return createStackTraceElement (JvNewStringLatin1 (name),
115 JvNewStringLatin1 (file_name));
116 }
117#endif
118 return NULL;
119}
120
121java::lang::StackTraceElement *
122gnu::gcj::runtime::NameFinder::lookupInterp(RawData* addrs, jint n)
123{
124#ifdef INTERPRETER
125 _Jv_frame_info *stack = (_Jv_frame_info *) addrs;
126 if (stack[n].interp == NULL)
127 return NULL;
128
129 _Jv_InterpMethod *meth
130 = reinterpret_cast<_Jv_InterpMethod *> (stack[n].interp);
131 java::lang::StringBuffer *sb = new java::lang::StringBuffer();
132 sb->append(_Jv_NewStringUtf8Const(meth->self->name));
133 sb->append(_Jv_NewStringUtf8Const(meth->self->signature));
134 // FIXME: source file name and line number can be found from
135 // bytecode debug information. But currently we don't keep that
136 // around.
137 // FIXME: is using the defining class correct here?
138 java::lang::String *className = meth->defining_class->getName();
139 java::lang::String *methodName
140 = demangleInterpreterMethod(sb->toString(), className);
141 return new java::lang::StackTraceElement(NULL, -1,
142 className, methodName, false);
143#else // INTERPRETER
144 return NULL;
145#endif // INTERPRETER
146}
Note: See TracBrowser for help on using the repository browser.