VirtualBox

source: vbox/trunk/src/VBox/Runtime/testcase/tstLdr-4.cpp@ 917

Last change on this file since 917 was 917, checked in by vboxsync, 18 years ago

Allow mixing of platform code.

  • Property svn:eol-style set to native
  • Property svn:keywords set to Id
File size: 7.3 KB
Line 
1/* $Id: tstLdr-4.cpp 917 2007-02-15 01:55:55Z vboxsync $ */
2/** @file
3 * InnoTek Portable Runtime - Testcase for RTLdrOpen using ldrLdrObjR0.r0.
4 */
5
6/*
7 * Copyright (C) 2006 InnoTek Systemberatung GmbH
8 *
9 * This file is part of VirtualBox Open Source Edition (OSE), as
10 * available from http://www.virtualbox.org. This file is free software;
11 * you can redistribute it and/or modify it under the terms of the GNU
12 * General Public License as published by the Free Software Foundation,
13 * in version 2 as it comes in the "COPYING" file of the VirtualBox OSE
14 * distribution. VirtualBox OSE is distributed in the hope that it will
15 * be useful, but WITHOUT ANY WARRANTY of any kind.
16 *
17 * If you received this file as part of a commercial VirtualBox
18 * distribution, then only the terms of your commercial VirtualBox
19 * license agreement apply instead of the previous paragraph.
20 */
21
22
23/*******************************************************************************
24* Header Files *
25*******************************************************************************/
26#include <iprt/ldr.h>
27#include <iprt/alloc.h>
28#include <iprt/stream.h>
29#include <iprt/assert.h>
30#include <iprt/runtime.h>
31#include <iprt/err.h>
32#include <iprt/string.h>
33
34
35extern "C" DECLEXPORT(int) DisasmTest1(void);
36
37
38/**
39 * Resolve an external symbol during RTLdrGetBits().
40 *
41 * @returns iprt status code.
42 * @param hLdrMod The loader module handle.
43 * @param pszModule Module name.
44 * @param pszSymbol Symbol name, NULL if uSymbol should be used.
45 * @param uSymbol Symbol ordinal, ~0 if pszSymbol should be used.
46 * @param pValue Where to store the symbol value (address).
47 * @param pvUser User argument.
48 */
49static DECLCALLBACK(int) testGetImport(RTLDRMOD hLdrMod, const char *pszModule, const char *pszSymbol, unsigned uSymbol, RTUINTPTR *pValue, void *pvUser)
50{
51 if ( !strcmp(pszSymbol, "AssertMsg1") || !strcmp(pszSymbol, "_AssertMsg1"))
52 *pValue = (uintptr_t)AssertMsg1;
53 else if (!strcmp(pszSymbol, "AssertMsg2") || !strcmp(pszSymbol, "_AssertMsg2"))
54 *pValue = (uintptr_t)AssertMsg2;
55 else if (!strcmp(pszSymbol, "RTLogDefaultInstance") || !strcmp(pszSymbol, "_RTLogDefaultInstance"))
56 *pValue = (uintptr_t)RTLogDefaultInstance;
57 else if (!strcmp(pszSymbol, "MyPrintf") || !strcmp(pszSymbol, "_MyPrintf"))
58 *pValue = (uintptr_t)RTPrintf;
59 else
60 {
61 RTPrintf("tstLdr-4: Unexpected import '%s'!\n", pszSymbol);
62 return VERR_SYMBOL_NOT_FOUND;
63 }
64 return VINF_SUCCESS;
65}
66
67
68/**
69 * One test iteration with one file.
70 *
71 * The test is very simple, we load the the file three times
72 * into two different regions. The first two into each of the
73 * regions the for compare usage. The third is loaded into one
74 * and then relocated between the two and other locations a few times.
75 *
76 * @returns number of errors.
77 * @param pszFilename The file to load the mess with.
78 */
79static int testLdrOne(const char *pszFilename)
80{
81 int cErrors = 0;
82 size_t cbImage = 0;
83 struct Load
84 {
85 RTLDRMOD hLdrMod;
86 void *pvBits;
87 char *pszName;
88 } aLoads[6] =
89 {
90 { NULL, NULL, "foo" },
91 { NULL, NULL, "bar" },
92 { NULL, NULL, "foobar" },
93 { NULL, NULL, "kLdr-foo" },
94 { NULL, NULL, "kLdr-bar" },
95 { NULL, NULL, "kLdr-foobar" }
96 };
97 unsigned i;
98 int rc;
99
100 /*
101 * Load them.
102 */
103 for (i = 0; i < ELEMENTS(aLoads); i++)
104 {
105 if (!strncmp(aLoads[i].pszName, "kLdr-", sizeof("kLdr-") - 1))
106 rc = RTLdrOpenkLdr(pszFilename, &aLoads[i].hLdrMod);
107 else
108 rc = RTLdrOpen(pszFilename, &aLoads[i].hLdrMod);
109 if (RT_FAILURE(rc))
110 {
111 RTPrintf("tstLdr-4: Failed to open '%s'/%d, rc=%Rrc. aborting test.\n", pszFilename, i, rc);
112 Assert(aLoads[i].hLdrMod == NIL_RTLDRMOD);
113 cErrors++;
114 break;
115 }
116
117 /* size it */
118 size_t cb = RTLdrSize(aLoads[i].hLdrMod);
119 if (cbImage && cb != cbImage)
120 {
121 RTPrintf("tstLdr-4: Size mismatch '%s'/%d. aborting test.\n", pszFilename, i);
122 cErrors++;
123 break;
124 }
125 cbImage = cb;
126
127 /* Allocate bits. */
128 aLoads[i].pvBits = RTMemAlloc(cb);
129 if (!aLoads[i].pvBits)
130 {
131 RTPrintf("tstLdr-4: Out of memory '%s'/%d cbImage=%d. aborting test.\n", pszFilename, i, cbImage);
132 cErrors++;
133 break;
134 }
135
136 /* Get the bits. */
137 rc = RTLdrGetBits(aLoads[i].hLdrMod, aLoads[i].pvBits, (uintptr_t)aLoads[i].pvBits, testGetImport, NULL);
138 if (RT_FAILURE(rc))
139 {
140 RTPrintf("tstLdr-4: Failed to get bits for '%s'/%d, rc=%Rrc. aborting test\n", pszFilename, i, rc);
141 cErrors++;
142 break;
143 }
144 }
145
146 /*
147 * Execute the code.
148 */
149 if (!cErrors)
150 {
151 for (i = 0; i < ELEMENTS(aLoads); i += 1)
152 {
153 /* get the pointer. */
154 RTUINTPTR Value;
155 rc = RTLdrGetSymbolEx(aLoads[i].hLdrMod, aLoads[i].pvBits, (uintptr_t)aLoads[i].pvBits, "DisasmTest1", &Value);
156 if (rc == VERR_SYMBOL_NOT_FOUND)
157 rc = RTLdrGetSymbolEx(aLoads[i].hLdrMod, aLoads[i].pvBits, (uintptr_t)aLoads[i].pvBits, "_DisasmTest1", &Value);
158 if (RT_FAILURE(rc))
159 {
160 RTPrintf("tstLdr-4: Failed to get symbol \"Test1\" from load #%d: %Rrc\n", i, rc);
161 cErrors++;
162 break;
163 }
164 DECLCALLBACKPTR(int, pfnDisasmTest1)(void) = (DECLCALLBACKPTR(int, )(void))(uintptr_t)Value; /* eeeh. */
165 RTPrintf("tstLdr-4: pfnDisasmTest1=%p / add-symbol-file %s %#x\n", pfnDisasmTest1, pszFilename, aLoads[i].pvBits);
166
167 /* call the test function. */
168 rc = pfnDisasmTest1();
169 if (rc)
170 {
171 RTPrintf("tstLdr-4: load #%d Test1 -> %#x\n", i, rc);
172 cErrors++;
173 }
174 }
175 }
176
177
178 /*
179 * Clean up.
180 */
181 for (i = 0; i < ELEMENTS(aLoads); i++)
182 {
183 if (aLoads[i].pvBits)
184 RTMemFree(aLoads[i].pvBits);
185 if (aLoads[i].hLdrMod)
186 {
187 int rc = RTLdrClose(aLoads[i].hLdrMod);
188 if (RT_FAILURE(rc))
189 {
190 RTPrintf("tstLdr-4: Failed to close '%s' i=%d, rc=%Rrc.\n", pszFilename, i, rc);
191 cErrors++;
192 }
193 }
194 }
195
196 return cErrors;
197}
198
199
200
201int main(int argc, char **argv)
202{
203 int cErrors = 0;
204 RTR3Init();
205
206 /*
207 * Sanity check.
208 */
209 int rc = DisasmTest1();
210 if (rc)
211 {
212 RTPrintf("tstLdr-4: FATAL ERROR - DisasmTest1 is buggy: rc=%#x\n", rc);
213 return 1;
214 }
215
216 /*
217 * Execute the test.
218 */
219 char szPath[RTPATH_MAX];
220 rc = RTPathProgram(szPath, sizeof(szPath) - sizeof("/tstLdrObjR0.r0"));
221 if (RT_SUCCESS(rc))
222 {
223 strcat(szPath, "/tstLdrObjR0.r0");
224 RTPrintf("tstLdr-4: TESTING '%s'...\n", szPath);
225 cErrors += testLdrOne(szPath);
226 }
227 else
228 {
229 RTPrintf("tstLdr-4: RTPathProgram -> %Rrc\n", rc);
230 cErrors++;
231 }
232
233 /*
234 * Test result summary.
235 */
236 if (!cErrors)
237 RTPrintf("tstLdr-4: SUCCESS\n");
238 else
239 RTPrintf("tstLdr-4: FAILURE - %d errors\n", cErrors);
240 return !!cErrors;
241}
Note: See TracBrowser for help on using the repository browser.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette