Direct-BT v3.3.0-1-gc2d430c
Direct-BT - Direct Bluetooth Programming.
TestElfReader01.java
Go to the documentation of this file.
1/**
2 * Author: Sven Gothel <sgothel@jausoft.com>
3 * Copyright (c) 2021 Gothel Software e.K.
4 * Copyright (c) 2013 Gothel Software e.K.
5 * Copyright (c) 2013 JogAmp Community.
6 *
7 * Permission is hereby granted, free of charge, to any person obtaining
8 * a copy of this software and associated documentation files (the
9 * "Software"), to deal in the Software without restriction, including
10 * without limitation the rights to use, copy, modify, merge, publish,
11 * distribute, sublicense, and/or sell copies of the Software, and to
12 * permit persons to whom the Software is furnished to do so, subject to
13 * the following conditions:
14 *
15 * The above copyright notice and this permission notice shall be
16 * included in all copies or substantial portions of the Software.
17 *
18 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
19 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
20 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
21 * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
22 * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
23 * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
24 * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
25 */
26package jau.test.sys.elf;
27
28import java.io.BufferedOutputStream;
29import java.io.File;
30import java.io.FileOutputStream;
31import java.io.IOException;
32import java.io.OutputStream;
33import java.io.RandomAccessFile;
34import java.nio.file.FileSystems;
35import java.nio.file.Files;
36import java.nio.file.Path;
37import java.util.List;
38
39import org.jau.sys.JNILibrary;
40import org.jau.sys.PlatformProps;
41import org.jau.sys.RuntimeProps;
42import org.jau.sys.PlatformTypes.OSType;
43import org.jau.sys.elf.ElfHeaderPart1;
44import org.jau.sys.elf.ElfHeaderPart2;
45import org.jau.sys.elf.Section;
46import org.jau.sys.elf.SectionArmAttributes;
47import org.jau.sys.elf.SectionHeader;
48import org.junit.FixMethodOrder;
49import org.junit.Test;
50import org.junit.runners.MethodSorters;
51
52import jau.test.junit.util.JunitTracer;
53
54@FixMethodOrder(MethodSorters.NAME_ASCENDING)
55public class TestElfReader01 extends JunitTracer {
56 public static String GNU_LINUX_SELF_EXE = "/proc/self/exe";
57 public static String ARM_HF_EXE = "tst-exe-armhf";
58 public static String ARM_SF_EXE = "tst-exe-arm";
59 static File userFile = null;
60
61 private static boolean checkFileReadAccess(final File file) {
62 try {
63 return file.isFile() && file.canRead();
64 } catch (final Throwable t) { }
65 return false;
66 }
67 static File findJVMLib(final String libName) {
68 final ClassLoader cl = TestElfReader01.class.getClassLoader();
69 final List<String> possibleLibPaths = JNILibrary.enumerateLibraryPaths(libName,
70 true /* searchSystemPath */, true /* searchSystemPathFirst */, cl);
71 for(int i=0; i<possibleLibPaths.size(); i++) {
72 final String libPath = possibleLibPaths.get(i);
73 final File lib = new File(libPath);
74 System.err.println("XXX2 #"+i+": test "+lib);
75 if( checkFileReadAccess(lib) ) {
76 return lib;
77 }
78 System.err.println("XXX2 #"+i+": "+lib+" not readable");
79 }
80 return null;
81 }
82
83 @Test
84 public void test01GNULinuxSelfExe () throws IOException {
85 if( null == userFile ) {
86 if( OSType.LINUX == PlatformProps.OS ) {
87 /**
88 * Directly using the `/proc/self/exe` via RandomAccessFile within ElfHeaderPart1 leads to a segmentation fault
89 * when using qemu binfmt_misc for armhf or aarch64 (cross build and test)!
90 *
91 * Hence we use the resolved link's exe-file, see below - don't ask ;-)
92 *
93 final File f = new File(GNU_LINUX_SELF_EXE);
94 if( checkFileReadAccess(f) ) {
95 testElfHeaderImpl(f, false);
96 }
97 */
98 final Path exe_symlink = FileSystems.getDefault().getPath("/proc/self/exe");
99 if( Files.isSymbolicLink(exe_symlink) ) {
100 final Path exe_path = Files.readSymbolicLink(exe_symlink);
101 final File f = exe_path.toFile();
102 if( checkFileReadAccess(f) ) {
103 System.err.println("ElfFile: "+exe_symlink+" -> "+exe_path+" -> "+f);
104 testElfHeaderImpl(f, false);
105 }
106 } else {
107 System.err.println("ElfFile: "+exe_symlink+" -> NULL");
108 }
109 }
110 }
111 }
112
113 @Test
114 public void test02JavaLib () throws IOException {
115 if( null == userFile ) {
116 File jvmLib = findJVMLib("java");
117 if( null == jvmLib ) {
118 jvmLib = findJVMLib("jvm");
119 }
120 if( null != jvmLib ) {
121 testElfHeaderImpl(jvmLib, false);
122 }
123 }
124 }
125
126 @Test
127 public void test99UserFile() throws IOException {
128 if( null != userFile ) {
129 testElfHeaderImpl(userFile, false);
130 }
131 }
132
133 void testElfHeaderImpl(final File file, final boolean fileOutSections) throws IOException {
134 RuntimeProps.initSingleton();
135 System.err.println("Test file "+file.getAbsolutePath());
136 final RandomAccessFile in = new RandomAccessFile(file, "r");
137 try {
138 final ElfHeaderPart1 eh1;
139 final ElfHeaderPart2 eh2;
140 try {
141 eh1 = ElfHeaderPart1.read(PlatformProps.OS, in);
142 eh2 = ElfHeaderPart2.read(eh1, in);
143 } catch (final Exception e) {
144 System.err.println("Probably not an ELF file - or not in current format: (caught) "+e.getMessage());
145 e.printStackTrace();
146 return;
147 }
148 int i=0;
149 System.err.println(eh1);
150 System.err.println(eh2);
151 System.err.println("SH entsz "+eh2.raw.getE_shentsize());
152 System.err.println("SH off "+toHexString(eh2.raw.getE_shoff()));
153 System.err.println("SH strndx "+eh2.raw.getE_shstrndx());
154 System.err.println("SH num "+eh2.sht.length);
155 if( 0 < eh2.sht.length ) {
156 System.err.println("SH size "+eh2.sht[0].raw.getBuffer().limit());
157 }
158 {
159 final SectionHeader sh = eh2.getSectionHeader(SectionHeader.SHT_ARM_ATTRIBUTES);
160 boolean abiVFPArgsAcceptsVFPVariant = false;
161 if( null != sh ) {
162 final SectionArmAttributes sArmAttrs = (SectionArmAttributes) sh.readSection(in);
163 final SectionArmAttributes.Attribute abiVFPArgsAttr = sArmAttrs.get(SectionArmAttributes.Tag.ABI_VFP_args);
164 if( null != abiVFPArgsAttr ) {
165 abiVFPArgsAcceptsVFPVariant = SectionArmAttributes.abiVFPArgsAcceptsVFPVariant(abiVFPArgsAttr.getULEB128());
166 }
167 }
168 System.err.println("abiVFPArgsAcceptsVFPVariant "+abiVFPArgsAcceptsVFPVariant);
169 }
170 for(i=0; i<eh2.sht.length; i++) {
171 final SectionHeader sh = eh2.sht[i];
172 System.err.println(sh);
173 final int type = sh.getType();
174 if( SectionHeader.SHT_STRTAB == type ) {
175 dumpSection(in, sh, "SHT_STRTAB", fileOutSections);
176 } else if( SectionHeader.SHT_ARM_ATTRIBUTES == type ) {
177 dumpSection(in, sh, "SHT_ARM_ATTRIBUTES", fileOutSections);
178 }
179 }
180 } finally {
181 in.close();
182 }
183 }
184
185 static void dumpSection(final RandomAccessFile in, final SectionHeader sh, final String name, final boolean fileOut) throws IllegalArgumentException, IOException {
186 final Section s = sh.readSection(in);
187 if(fileOut) {
188 final File outFile = new File("ElfSection-"+sh.getIndex()+"-"+name);
189 final OutputStream out = new BufferedOutputStream(new FileOutputStream(outFile));
190 try {
191 out.write(s.data, s.offset, s.length);
192 } finally {
193 out.close();
194 }
195 }
196 System.err.println(name+": read "+s.length+", "+s);
197 }
198
199 public static void main(final String args[]) throws IOException {
200 for(int i=0; i<args.length; i++) {
201 if(args[i].equals("-file")) {
202 i++;
203 userFile = new File(args[i]);
204 }
205 }
206 final String tstname = TestElfReader01.class.getName();
207 org.junit.runner.JUnitCore.main(tstname);
208 }
209
210 static String toHexString(final int i) { return "0x"+Integer.toHexString(i); }
211 static String toHexString(final long i) { return "0x"+Long.toHexString(i); }
212
213}
static void main(final String args[])