38856343f90103280eb83b5e697f9f618b407d83vboxsync/* $Id$ */
38856343f90103280eb83b5e697f9f618b407d83vboxsync/** @file
5b281ba489ca18f0380d7efc7a5108b606cce449vboxsync * IPRT - Testcase for RTLdrOpen using ldrLdrObjR0.r0.
38856343f90103280eb83b5e697f9f618b407d83vboxsync */
38856343f90103280eb83b5e697f9f618b407d83vboxsync
38856343f90103280eb83b5e697f9f618b407d83vboxsync/*
c58f1213e628a545081c70e26c6b67a841cff880vboxsync * Copyright (C) 2006-2012 Oracle Corporation
38856343f90103280eb83b5e697f9f618b407d83vboxsync *
38856343f90103280eb83b5e697f9f618b407d83vboxsync * This file is part of VirtualBox Open Source Edition (OSE), as
38856343f90103280eb83b5e697f9f618b407d83vboxsync * available from http://www.virtualbox.org. This file is free software;
38856343f90103280eb83b5e697f9f618b407d83vboxsync * you can redistribute it and/or modify it under the terms of the GNU
a16eb14ad7a4b5ef91ddc22d3e8e92d930f736fcvboxsync * General Public License (GPL) as published by the Free Software
a16eb14ad7a4b5ef91ddc22d3e8e92d930f736fcvboxsync * Foundation, in version 2 as it comes in the "COPYING" file of the
a16eb14ad7a4b5ef91ddc22d3e8e92d930f736fcvboxsync * VirtualBox OSE distribution. VirtualBox OSE is distributed in the
a16eb14ad7a4b5ef91ddc22d3e8e92d930f736fcvboxsync * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
a16eb14ad7a4b5ef91ddc22d3e8e92d930f736fcvboxsync *
a16eb14ad7a4b5ef91ddc22d3e8e92d930f736fcvboxsync * The contents of this file may alternatively be used under the terms
a16eb14ad7a4b5ef91ddc22d3e8e92d930f736fcvboxsync * of the Common Development and Distribution License Version 1.0
a16eb14ad7a4b5ef91ddc22d3e8e92d930f736fcvboxsync * (CDDL) only, as it comes in the "COPYING.CDDL" file of the
a16eb14ad7a4b5ef91ddc22d3e8e92d930f736fcvboxsync * VirtualBox OSE distribution, in which case the provisions of the
a16eb14ad7a4b5ef91ddc22d3e8e92d930f736fcvboxsync * CDDL are applicable instead of those of the GPL.
a16eb14ad7a4b5ef91ddc22d3e8e92d930f736fcvboxsync *
a16eb14ad7a4b5ef91ddc22d3e8e92d930f736fcvboxsync * You may elect to license modified versions of this file under the
a16eb14ad7a4b5ef91ddc22d3e8e92d930f736fcvboxsync * terms and conditions of either the GPL or the CDDL or both.
38856343f90103280eb83b5e697f9f618b407d83vboxsync */
38856343f90103280eb83b5e697f9f618b407d83vboxsync
38856343f90103280eb83b5e697f9f618b407d83vboxsync
38856343f90103280eb83b5e697f9f618b407d83vboxsync/*******************************************************************************
38856343f90103280eb83b5e697f9f618b407d83vboxsync* Header Files *
38856343f90103280eb83b5e697f9f618b407d83vboxsync*******************************************************************************/
38856343f90103280eb83b5e697f9f618b407d83vboxsync#include <iprt/ldr.h>
38856343f90103280eb83b5e697f9f618b407d83vboxsync#include <iprt/alloc.h>
5eabf773597082761832bc0a32b3660e8771f9f1vboxsync#include <iprt/log.h>
38856343f90103280eb83b5e697f9f618b407d83vboxsync#include <iprt/stream.h>
38856343f90103280eb83b5e697f9f618b407d83vboxsync#include <iprt/assert.h>
5eabf773597082761832bc0a32b3660e8771f9f1vboxsync#include <iprt/param.h>
5eabf773597082761832bc0a32b3660e8771f9f1vboxsync#include <iprt/path.h>
5eabf773597082761832bc0a32b3660e8771f9f1vboxsync#include <iprt/initterm.h>
38856343f90103280eb83b5e697f9f618b407d83vboxsync#include <iprt/err.h>
38856343f90103280eb83b5e697f9f618b407d83vboxsync#include <iprt/string.h>
38856343f90103280eb83b5e697f9f618b407d83vboxsync
38856343f90103280eb83b5e697f9f618b407d83vboxsync
38856343f90103280eb83b5e697f9f618b407d83vboxsyncextern "C" DECLEXPORT(int) DisasmTest1(void);
38856343f90103280eb83b5e697f9f618b407d83vboxsync
38856343f90103280eb83b5e697f9f618b407d83vboxsync
38856343f90103280eb83b5e697f9f618b407d83vboxsync/**
38856343f90103280eb83b5e697f9f618b407d83vboxsync * Resolve an external symbol during RTLdrGetBits().
38856343f90103280eb83b5e697f9f618b407d83vboxsync *
38856343f90103280eb83b5e697f9f618b407d83vboxsync * @returns iprt status code.
38856343f90103280eb83b5e697f9f618b407d83vboxsync * @param hLdrMod The loader module handle.
38856343f90103280eb83b5e697f9f618b407d83vboxsync * @param pszModule Module name.
38856343f90103280eb83b5e697f9f618b407d83vboxsync * @param pszSymbol Symbol name, NULL if uSymbol should be used.
38856343f90103280eb83b5e697f9f618b407d83vboxsync * @param uSymbol Symbol ordinal, ~0 if pszSymbol should be used.
38856343f90103280eb83b5e697f9f618b407d83vboxsync * @param pValue Where to store the symbol value (address).
38856343f90103280eb83b5e697f9f618b407d83vboxsync * @param pvUser User argument.
38856343f90103280eb83b5e697f9f618b407d83vboxsync */
38856343f90103280eb83b5e697f9f618b407d83vboxsyncstatic DECLCALLBACK(int) testGetImport(RTLDRMOD hLdrMod, const char *pszModule, const char *pszSymbol, unsigned uSymbol, RTUINTPTR *pValue, void *pvUser)
38856343f90103280eb83b5e697f9f618b407d83vboxsync{
a7aa94e0115a73841f34ebbfa00f63fa1904e51fvboxsync if ( !strcmp(pszSymbol, "RTAssertMsg1Weak") || !strcmp(pszSymbol, "_RTAssertMsg1Weak"))
a7aa94e0115a73841f34ebbfa00f63fa1904e51fvboxsync *pValue = (uintptr_t)RTAssertMsg1Weak;
a7aa94e0115a73841f34ebbfa00f63fa1904e51fvboxsync else if (!strcmp(pszSymbol, "RTAssertMsg2Weak") || !strcmp(pszSymbol, "_RTAssertMsg2Weak"))
a7aa94e0115a73841f34ebbfa00f63fa1904e51fvboxsync *pValue = (uintptr_t)RTAssertMsg1Weak;
10f18618390096a9c968016b6ca94d77b91618fbvboxsync else if (!strcmp(pszSymbol, "RTAssertMsg1") || !strcmp(pszSymbol, "_RTAssertMsg1"))
10f18618390096a9c968016b6ca94d77b91618fbvboxsync *pValue = (uintptr_t)RTAssertMsg1;
10f18618390096a9c968016b6ca94d77b91618fbvboxsync else if (!strcmp(pszSymbol, "RTAssertMsg2") || !strcmp(pszSymbol, "_RTAssertMsg2"))
10f18618390096a9c968016b6ca94d77b91618fbvboxsync *pValue = (uintptr_t)RTAssertMsg2;
10f18618390096a9c968016b6ca94d77b91618fbvboxsync else if (!strcmp(pszSymbol, "RTAssertMsg2V") || !strcmp(pszSymbol, "_RTAssertMsg2V"))
10f18618390096a9c968016b6ca94d77b91618fbvboxsync *pValue = (uintptr_t)RTAssertMsg2V;
10f18618390096a9c968016b6ca94d77b91618fbvboxsync else if (!strcmp(pszSymbol, "RTAssertMayPanic") || !strcmp(pszSymbol, "_RTAssertMayPanic"))
10f18618390096a9c968016b6ca94d77b91618fbvboxsync *pValue = (uintptr_t)RTAssertMayPanic;
4f5c03319462e58ce23cdd7d37d17a72e57f7105vboxsync else if (!strcmp(pszSymbol, "RTLogDefaultInstance") || !strcmp(pszSymbol, "_RTLogDefaultInstance"))
38856343f90103280eb83b5e697f9f618b407d83vboxsync *pValue = (uintptr_t)RTLogDefaultInstance;
900e06286caa6d682ef12fc235720d2d8d568df4vboxsync else if (!strcmp(pszSymbol, "RTLogLoggerExV") || !strcmp(pszSymbol, "_RTLogLoggerExV"))
900e06286caa6d682ef12fc235720d2d8d568df4vboxsync *pValue = (uintptr_t)RTLogLoggerExV;
900e06286caa6d682ef12fc235720d2d8d568df4vboxsync else if (!strcmp(pszSymbol, "RTLogPrintfV") || !strcmp(pszSymbol, "_RTLogPrintfV"))
900e06286caa6d682ef12fc235720d2d8d568df4vboxsync *pValue = (uintptr_t)RTLogPrintfV;
900e06286caa6d682ef12fc235720d2d8d568df4vboxsync else if (!strcmp(pszSymbol, "RTR0AssertPanicSystem")|| !strcmp(pszSymbol, "_RTR0AssertPanicSystem"))
900e06286caa6d682ef12fc235720d2d8d568df4vboxsync *pValue = (uintptr_t)0;
4f5c03319462e58ce23cdd7d37d17a72e57f7105vboxsync else if (!strcmp(pszSymbol, "MyPrintf") || !strcmp(pszSymbol, "_MyPrintf"))
38856343f90103280eb83b5e697f9f618b407d83vboxsync *pValue = (uintptr_t)RTPrintf;
38856343f90103280eb83b5e697f9f618b407d83vboxsync else
38856343f90103280eb83b5e697f9f618b407d83vboxsync {
38856343f90103280eb83b5e697f9f618b407d83vboxsync RTPrintf("tstLdr-4: Unexpected import '%s'!\n", pszSymbol);
38856343f90103280eb83b5e697f9f618b407d83vboxsync return VERR_SYMBOL_NOT_FOUND;
38856343f90103280eb83b5e697f9f618b407d83vboxsync }
38856343f90103280eb83b5e697f9f618b407d83vboxsync return VINF_SUCCESS;
38856343f90103280eb83b5e697f9f618b407d83vboxsync}
38856343f90103280eb83b5e697f9f618b407d83vboxsync
38856343f90103280eb83b5e697f9f618b407d83vboxsync
38856343f90103280eb83b5e697f9f618b407d83vboxsync/**
38856343f90103280eb83b5e697f9f618b407d83vboxsync * One test iteration with one file.
38856343f90103280eb83b5e697f9f618b407d83vboxsync *
9621896680fea9b2078823e8ef2e64cec5bf2da0vboxsync * The test is very simple, we load the file three times
38856343f90103280eb83b5e697f9f618b407d83vboxsync * into two different regions. The first two into each of the
38856343f90103280eb83b5e697f9f618b407d83vboxsync * regions the for compare usage. The third is loaded into one
38856343f90103280eb83b5e697f9f618b407d83vboxsync * and then relocated between the two and other locations a few times.
38856343f90103280eb83b5e697f9f618b407d83vboxsync *
38856343f90103280eb83b5e697f9f618b407d83vboxsync * @returns number of errors.
38856343f90103280eb83b5e697f9f618b407d83vboxsync * @param pszFilename The file to load the mess with.
38856343f90103280eb83b5e697f9f618b407d83vboxsync */
38856343f90103280eb83b5e697f9f618b407d83vboxsyncstatic int testLdrOne(const char *pszFilename)
38856343f90103280eb83b5e697f9f618b407d83vboxsync{
38856343f90103280eb83b5e697f9f618b407d83vboxsync int cErrors = 0;
38856343f90103280eb83b5e697f9f618b407d83vboxsync size_t cbImage = 0;
38856343f90103280eb83b5e697f9f618b407d83vboxsync struct Load
38856343f90103280eb83b5e697f9f618b407d83vboxsync {
38856343f90103280eb83b5e697f9f618b407d83vboxsync RTLDRMOD hLdrMod;
38856343f90103280eb83b5e697f9f618b407d83vboxsync void *pvBits;
418b9db49fbc652ef9c3f030fdc0f1a322403d95vboxsync size_t cbBits;
7258e84ec2fa7ecaf94e1a244bd6d2cf6b3a40a4vboxsync const char *pszName;
38856343f90103280eb83b5e697f9f618b407d83vboxsync } aLoads[6] =
38856343f90103280eb83b5e697f9f618b407d83vboxsync {
418b9db49fbc652ef9c3f030fdc0f1a322403d95vboxsync { NULL, NULL, 0, "foo" },
418b9db49fbc652ef9c3f030fdc0f1a322403d95vboxsync { NULL, NULL, 0, "bar" },
418b9db49fbc652ef9c3f030fdc0f1a322403d95vboxsync { NULL, NULL, 0, "foobar" },
418b9db49fbc652ef9c3f030fdc0f1a322403d95vboxsync { NULL, NULL, 0, "kLdr-foo" },
418b9db49fbc652ef9c3f030fdc0f1a322403d95vboxsync { NULL, NULL, 0, "kLdr-bar" },
418b9db49fbc652ef9c3f030fdc0f1a322403d95vboxsync { NULL, NULL, 0, "kLdr-foobar" }
38856343f90103280eb83b5e697f9f618b407d83vboxsync };
38856343f90103280eb83b5e697f9f618b407d83vboxsync unsigned i;
38856343f90103280eb83b5e697f9f618b407d83vboxsync int rc;
38856343f90103280eb83b5e697f9f618b407d83vboxsync
38856343f90103280eb83b5e697f9f618b407d83vboxsync /*
38856343f90103280eb83b5e697f9f618b407d83vboxsync * Load them.
38856343f90103280eb83b5e697f9f618b407d83vboxsync */
e9a584ee0777ab2612e206eeec264ccb1a8ce333vboxsync for (i = 0; i < RT_ELEMENTS(aLoads); i++)
38856343f90103280eb83b5e697f9f618b407d83vboxsync {
1939436fa43cbf7f5cdc05a3830ed624d5fe4a6avboxsync if (!strncmp(aLoads[i].pszName, RT_STR_TUPLE("kLdr-")))
6c2750d8e30830bf114880ca33922b108ab3e942vboxsync rc = RTLdrOpenkLdr(pszFilename, 0, RTLDRARCH_WHATEVER, &aLoads[i].hLdrMod);
38856343f90103280eb83b5e697f9f618b407d83vboxsync else
6c2750d8e30830bf114880ca33922b108ab3e942vboxsync rc = RTLdrOpen(pszFilename, 0, RTLDRARCH_WHATEVER, &aLoads[i].hLdrMod);
38856343f90103280eb83b5e697f9f618b407d83vboxsync if (RT_FAILURE(rc))
38856343f90103280eb83b5e697f9f618b407d83vboxsync {
38856343f90103280eb83b5e697f9f618b407d83vboxsync RTPrintf("tstLdr-4: Failed to open '%s'/%d, rc=%Rrc. aborting test.\n", pszFilename, i, rc);
38856343f90103280eb83b5e697f9f618b407d83vboxsync Assert(aLoads[i].hLdrMod == NIL_RTLDRMOD);
38856343f90103280eb83b5e697f9f618b407d83vboxsync cErrors++;
38856343f90103280eb83b5e697f9f618b407d83vboxsync break;
38856343f90103280eb83b5e697f9f618b407d83vboxsync }
38856343f90103280eb83b5e697f9f618b407d83vboxsync
38856343f90103280eb83b5e697f9f618b407d83vboxsync /* size it */
38856343f90103280eb83b5e697f9f618b407d83vboxsync size_t cb = RTLdrSize(aLoads[i].hLdrMod);
38856343f90103280eb83b5e697f9f618b407d83vboxsync if (cbImage && cb != cbImage)
38856343f90103280eb83b5e697f9f618b407d83vboxsync {
38856343f90103280eb83b5e697f9f618b407d83vboxsync RTPrintf("tstLdr-4: Size mismatch '%s'/%d. aborting test.\n", pszFilename, i);
38856343f90103280eb83b5e697f9f618b407d83vboxsync cErrors++;
38856343f90103280eb83b5e697f9f618b407d83vboxsync break;
38856343f90103280eb83b5e697f9f618b407d83vboxsync }
418b9db49fbc652ef9c3f030fdc0f1a322403d95vboxsync aLoads[i].cbBits = cbImage = cb;
38856343f90103280eb83b5e697f9f618b407d83vboxsync
38856343f90103280eb83b5e697f9f618b407d83vboxsync /* Allocate bits. */
900e06286caa6d682ef12fc235720d2d8d568df4vboxsync aLoads[i].pvBits = RTMemExecAlloc(cb);
38856343f90103280eb83b5e697f9f618b407d83vboxsync if (!aLoads[i].pvBits)
38856343f90103280eb83b5e697f9f618b407d83vboxsync {
38856343f90103280eb83b5e697f9f618b407d83vboxsync RTPrintf("tstLdr-4: Out of memory '%s'/%d cbImage=%d. aborting test.\n", pszFilename, i, cbImage);
38856343f90103280eb83b5e697f9f618b407d83vboxsync cErrors++;
38856343f90103280eb83b5e697f9f618b407d83vboxsync break;
38856343f90103280eb83b5e697f9f618b407d83vboxsync }
38856343f90103280eb83b5e697f9f618b407d83vboxsync
38856343f90103280eb83b5e697f9f618b407d83vboxsync /* Get the bits. */
38856343f90103280eb83b5e697f9f618b407d83vboxsync rc = RTLdrGetBits(aLoads[i].hLdrMod, aLoads[i].pvBits, (uintptr_t)aLoads[i].pvBits, testGetImport, NULL);
38856343f90103280eb83b5e697f9f618b407d83vboxsync if (RT_FAILURE(rc))
38856343f90103280eb83b5e697f9f618b407d83vboxsync {
38856343f90103280eb83b5e697f9f618b407d83vboxsync RTPrintf("tstLdr-4: Failed to get bits for '%s'/%d, rc=%Rrc. aborting test\n", pszFilename, i, rc);
38856343f90103280eb83b5e697f9f618b407d83vboxsync cErrors++;
38856343f90103280eb83b5e697f9f618b407d83vboxsync break;
38856343f90103280eb83b5e697f9f618b407d83vboxsync }
38856343f90103280eb83b5e697f9f618b407d83vboxsync }
38856343f90103280eb83b5e697f9f618b407d83vboxsync
38856343f90103280eb83b5e697f9f618b407d83vboxsync /*
38856343f90103280eb83b5e697f9f618b407d83vboxsync * Execute the code.
38856343f90103280eb83b5e697f9f618b407d83vboxsync */
38856343f90103280eb83b5e697f9f618b407d83vboxsync if (!cErrors)
38856343f90103280eb83b5e697f9f618b407d83vboxsync {
e9a584ee0777ab2612e206eeec264ccb1a8ce333vboxsync for (i = 0; i < RT_ELEMENTS(aLoads); i += 1)
38856343f90103280eb83b5e697f9f618b407d83vboxsync {
38856343f90103280eb83b5e697f9f618b407d83vboxsync /* get the pointer. */
38856343f90103280eb83b5e697f9f618b407d83vboxsync RTUINTPTR Value;
0c8e85263a357c44964520942cb5816ab1c2e69dvboxsync rc = RTLdrGetSymbolEx(aLoads[i].hLdrMod, aLoads[i].pvBits, (uintptr_t)aLoads[i].pvBits,
0c8e85263a357c44964520942cb5816ab1c2e69dvboxsync UINT32_MAX, "DisasmTest1", &Value);
4f5c03319462e58ce23cdd7d37d17a72e57f7105vboxsync if (rc == VERR_SYMBOL_NOT_FOUND)
0c8e85263a357c44964520942cb5816ab1c2e69dvboxsync rc = RTLdrGetSymbolEx(aLoads[i].hLdrMod, aLoads[i].pvBits, (uintptr_t)aLoads[i].pvBits,
0c8e85263a357c44964520942cb5816ab1c2e69dvboxsync UINT32_MAX, "_DisasmTest1", &Value);
38856343f90103280eb83b5e697f9f618b407d83vboxsync if (RT_FAILURE(rc))
38856343f90103280eb83b5e697f9f618b407d83vboxsync {
588f763595b21d28ce311148a618cc4ead630558vboxsync RTPrintf("tstLdr-4: Failed to get symbol \"DisasmTest1\" from load #%d: %Rrc\n", i, rc);
38856343f90103280eb83b5e697f9f618b407d83vboxsync cErrors++;
38856343f90103280eb83b5e697f9f618b407d83vboxsync break;
38856343f90103280eb83b5e697f9f618b407d83vboxsync }
5a78b426f7ac35147bee8d3a8821efc7343cbac7vboxsync DECLCALLBACKPTR(int, pfnDisasmTest1)(void) = (DECLCALLBACKPTR(int, RT_NOTHING)(void))(uintptr_t)Value; /* eeeh. */
38856343f90103280eb83b5e697f9f618b407d83vboxsync RTPrintf("tstLdr-4: pfnDisasmTest1=%p / add-symbol-file %s %#x\n", pfnDisasmTest1, pszFilename, aLoads[i].pvBits);
38856343f90103280eb83b5e697f9f618b407d83vboxsync
38856343f90103280eb83b5e697f9f618b407d83vboxsync /* call the test function. */
38856343f90103280eb83b5e697f9f618b407d83vboxsync rc = pfnDisasmTest1();
38856343f90103280eb83b5e697f9f618b407d83vboxsync if (rc)
38856343f90103280eb83b5e697f9f618b407d83vboxsync {
38856343f90103280eb83b5e697f9f618b407d83vboxsync RTPrintf("tstLdr-4: load #%d Test1 -> %#x\n", i, rc);
38856343f90103280eb83b5e697f9f618b407d83vboxsync cErrors++;
38856343f90103280eb83b5e697f9f618b407d83vboxsync }
38856343f90103280eb83b5e697f9f618b407d83vboxsync }
38856343f90103280eb83b5e697f9f618b407d83vboxsync }
38856343f90103280eb83b5e697f9f618b407d83vboxsync
38856343f90103280eb83b5e697f9f618b407d83vboxsync
38856343f90103280eb83b5e697f9f618b407d83vboxsync /*
38856343f90103280eb83b5e697f9f618b407d83vboxsync * Clean up.
38856343f90103280eb83b5e697f9f618b407d83vboxsync */
e9a584ee0777ab2612e206eeec264ccb1a8ce333vboxsync for (i = 0; i < RT_ELEMENTS(aLoads); i++)
38856343f90103280eb83b5e697f9f618b407d83vboxsync {
38856343f90103280eb83b5e697f9f618b407d83vboxsync if (aLoads[i].pvBits)
418b9db49fbc652ef9c3f030fdc0f1a322403d95vboxsync RTMemExecFree(aLoads[i].pvBits, aLoads[i].cbBits);
38856343f90103280eb83b5e697f9f618b407d83vboxsync if (aLoads[i].hLdrMod)
38856343f90103280eb83b5e697f9f618b407d83vboxsync {
8f2f51347c7b5fe7c697debe7c2e46b46dd16489vboxsync rc = RTLdrClose(aLoads[i].hLdrMod);
38856343f90103280eb83b5e697f9f618b407d83vboxsync if (RT_FAILURE(rc))
38856343f90103280eb83b5e697f9f618b407d83vboxsync {
38856343f90103280eb83b5e697f9f618b407d83vboxsync RTPrintf("tstLdr-4: Failed to close '%s' i=%d, rc=%Rrc.\n", pszFilename, i, rc);
38856343f90103280eb83b5e697f9f618b407d83vboxsync cErrors++;
38856343f90103280eb83b5e697f9f618b407d83vboxsync }
38856343f90103280eb83b5e697f9f618b407d83vboxsync }
38856343f90103280eb83b5e697f9f618b407d83vboxsync }
38856343f90103280eb83b5e697f9f618b407d83vboxsync
38856343f90103280eb83b5e697f9f618b407d83vboxsync return cErrors;
38856343f90103280eb83b5e697f9f618b407d83vboxsync}
38856343f90103280eb83b5e697f9f618b407d83vboxsync
38856343f90103280eb83b5e697f9f618b407d83vboxsync
38856343f90103280eb83b5e697f9f618b407d83vboxsync
38856343f90103280eb83b5e697f9f618b407d83vboxsyncint main(int argc, char **argv)
38856343f90103280eb83b5e697f9f618b407d83vboxsync{
38856343f90103280eb83b5e697f9f618b407d83vboxsync int cErrors = 0;
230bd8589bba39933ac5ec21482d6186d675e604vboxsync RTR3InitExe(argc, &argv, 0);
38856343f90103280eb83b5e697f9f618b407d83vboxsync
38856343f90103280eb83b5e697f9f618b407d83vboxsync /*
38856343f90103280eb83b5e697f9f618b407d83vboxsync * Sanity check.
38856343f90103280eb83b5e697f9f618b407d83vboxsync */
38856343f90103280eb83b5e697f9f618b407d83vboxsync int rc = DisasmTest1();
38856343f90103280eb83b5e697f9f618b407d83vboxsync if (rc)
38856343f90103280eb83b5e697f9f618b407d83vboxsync {
38856343f90103280eb83b5e697f9f618b407d83vboxsync RTPrintf("tstLdr-4: FATAL ERROR - DisasmTest1 is buggy: rc=%#x\n", rc);
38856343f90103280eb83b5e697f9f618b407d83vboxsync return 1;
38856343f90103280eb83b5e697f9f618b407d83vboxsync }
38856343f90103280eb83b5e697f9f618b407d83vboxsync
38856343f90103280eb83b5e697f9f618b407d83vboxsync /*
38856343f90103280eb83b5e697f9f618b407d83vboxsync * Execute the test.
38856343f90103280eb83b5e697f9f618b407d83vboxsync */
38856343f90103280eb83b5e697f9f618b407d83vboxsync char szPath[RTPATH_MAX];
c77e7bff89c7639353778366984d51ff165ea0e3vboxsync rc = RTPathExecDir(szPath, sizeof(szPath) - sizeof("/tstLdrObjR0.r0"));
38856343f90103280eb83b5e697f9f618b407d83vboxsync if (RT_SUCCESS(rc))
38856343f90103280eb83b5e697f9f618b407d83vboxsync {
38856343f90103280eb83b5e697f9f618b407d83vboxsync strcat(szPath, "/tstLdrObjR0.r0");
38856343f90103280eb83b5e697f9f618b407d83vboxsync RTPrintf("tstLdr-4: TESTING '%s'...\n", szPath);
38856343f90103280eb83b5e697f9f618b407d83vboxsync cErrors += testLdrOne(szPath);
38856343f90103280eb83b5e697f9f618b407d83vboxsync }
38856343f90103280eb83b5e697f9f618b407d83vboxsync else
38856343f90103280eb83b5e697f9f618b407d83vboxsync {
c77e7bff89c7639353778366984d51ff165ea0e3vboxsync RTPrintf("tstLdr-4: RTPathExecDir -> %Rrc\n", rc);
38856343f90103280eb83b5e697f9f618b407d83vboxsync cErrors++;
38856343f90103280eb83b5e697f9f618b407d83vboxsync }
38856343f90103280eb83b5e697f9f618b407d83vboxsync
38856343f90103280eb83b5e697f9f618b407d83vboxsync /*
38856343f90103280eb83b5e697f9f618b407d83vboxsync * Test result summary.
38856343f90103280eb83b5e697f9f618b407d83vboxsync */
38856343f90103280eb83b5e697f9f618b407d83vboxsync if (!cErrors)
38856343f90103280eb83b5e697f9f618b407d83vboxsync RTPrintf("tstLdr-4: SUCCESS\n");
38856343f90103280eb83b5e697f9f618b407d83vboxsync else
38856343f90103280eb83b5e697f9f618b407d83vboxsync RTPrintf("tstLdr-4: FAILURE - %d errors\n", cErrors);
38856343f90103280eb83b5e697f9f618b407d83vboxsync return !!cErrors;
38856343f90103280eb83b5e697f9f618b407d83vboxsync}