Skip to content
This repository has been archived by the owner on Jan 23, 2023. It is now read-only.

[x86/Linux] implement TheUMEntryPrestub #8589

Merged
merged 1 commit into from
Dec 12, 2016
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions src/vm/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -379,6 +379,7 @@ else(WIN32)
set(VM_SOURCES_WKS_ARCH_ASM
${ARCH_SOURCES_DIR}/asmhelpers.S
${ARCH_SOURCES_DIR}/gmsasm.S
${ARCH_SOURCES_DIR}/umthunkstub.S
)
elseif(CLR_CMAKE_TARGET_ARCH_ARM)
set(VM_SOURCES_WKS_ARCH_ASM
Expand Down
4 changes: 2 additions & 2 deletions src/vm/comdelegate.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1249,7 +1249,7 @@ PCODE COMDelegate::ConvertToCallback(MethodDesc* pMD)
// Get UMEntryThunk from appdomain thunkcache cache.
UMEntryThunk *pUMEntryThunk = GetAppDomain()->GetUMEntryThunkCache()->GetUMEntryThunk(pMD);

#ifdef _TARGET_X86_
#if defined(_TARGET_X86_) && !defined(FEATURE_STUBS_AS_IL)

// System.Runtime.InteropServices.NativeCallableAttribute
BYTE* pData = NULL;
Expand Down Expand Up @@ -1281,7 +1281,7 @@ PCODE COMDelegate::ConvertToCallback(MethodDesc* pMD)
pUMThunkMarshalInfo->SetCallingConvention(callConv);
}
}
#endif //_TARGET_X86_
#endif //_TARGET_X86_ && !FEATURE_STUBS_AS_IL

pCode = (PCODE)pUMEntryThunk->GetCode();
_ASSERTE(pCode != NULL);
Expand Down
16 changes: 8 additions & 8 deletions src/vm/dllimportcallback.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -164,7 +164,7 @@ EXTERN_C void STDCALL UM2MDoADCallBack(UMEntryThunk *pEntryThunk,
UNINSTALL_MANAGED_EXCEPTION_DISPATCHER;
}

#ifdef _TARGET_X86_
#if defined(_TARGET_X86_) && !defined(FEATURE_STUBS_AS_IL)

EXTERN_C VOID __cdecl UMThunkStubRareDisable();
EXTERN_C Thread* __stdcall CreateThreadBlockThrow();
Expand Down Expand Up @@ -1010,7 +1010,7 @@ Stub *UMThunkMarshInfo::CompileNExportThunk(LoaderHeap *pLoaderHeap, PInvokeStat
return pcpusl->Link(pLoaderHeap);
}

#else // _TARGET_X86_
#else // _TARGET_X86_ && !FEATURE_STUBS_AS_IL

PCODE UMThunkMarshInfo::GetExecStubEntryPoint()
{
Expand All @@ -1019,7 +1019,7 @@ PCODE UMThunkMarshInfo::GetExecStubEntryPoint()
return GetEEFuncEntryPoint(UMThunkStub);
}

#endif // _TARGET_X86_
#endif // _TARGET_X86_ && !FEATURE_STUBS_AS_IL

UMEntryThunkCache::UMEntryThunkCache(AppDomain *pDomain) :
m_crst(CrstUMEntryThunkCache),
Expand Down Expand Up @@ -1302,7 +1302,7 @@ UMThunkMarshInfo::~UMThunkMarshInfo()
}
CONTRACTL_END;

#ifdef _TARGET_X86_
#if defined(_TARGET_X86_) && !defined(FEATURE_STUBS_AS_IL)
if (m_pExecStub)
m_pExecStub->DecRef();
#endif
Expand Down Expand Up @@ -1364,7 +1364,7 @@ VOID UMThunkMarshInfo::LoadTimeInit(Signature sig, Module * pModule, MethodDesc
m_pModule = pModule;
m_sig = sig;

#ifdef _TARGET_X86_
#if defined(_TARGET_X86_) && !defined(FEATURE_STUBS_AS_IL)
INDEBUG(m_cbRetPop = 0xcccc;)
#endif
}
Expand Down Expand Up @@ -1407,7 +1407,7 @@ VOID UMThunkMarshInfo::RunTimeInit()
pFinalILStub = GetStubForInteropMethod(pMD, dwStubFlags, &pStubMD);
}

#ifdef _TARGET_X86_
#if defined(_TARGET_X86_) && !defined(FEATURE_STUBS_AS_IL)
PInvokeStaticSigInfo sigInfo;

if (pMD != NULL)
Expand Down Expand Up @@ -1458,7 +1458,7 @@ VOID UMThunkMarshInfo::RunTimeInit()
pFinalExecStub->DecRef();
}

#else // _TARGET_X86_
#else // _TARGET_X86_ && !FEATURE_STUBS_AS_IL

if (pFinalILStub == NULL)
{
Expand Down Expand Up @@ -1499,7 +1499,7 @@ VOID UMThunkMarshInfo::RunTimeInit()
//
m_cbActualArgSize = (pStubMD != NULL) ? pStubMD->AsDynamicMethodDesc()->GetNativeStackArgSize() : pMD->SizeOfArgStack();

#endif // _TARGET_X86_
#endif // _TARGET_X86_ && !FEATURE_STUBS_AS_IL

// Must be the last thing we set!
InterlockedCompareExchangeT<PCODE>(&m_pILStub, pFinalILStub, (PCODE)1);
Expand Down
16 changes: 8 additions & 8 deletions src/vm/dllimportcallback.h
Original file line number Diff line number Diff line change
Expand Up @@ -110,7 +110,7 @@ class UMThunkMarshInfo
return m_pMD;
}

#ifdef _TARGET_X86_
#if defined(_TARGET_X86_) && !defined(FEATURE_STUBS_AS_IL)
PCODE GetExecStubEntryPoint()
{
WRAPPER_NO_CONTRACT;
Expand Down Expand Up @@ -199,18 +199,18 @@ class UMThunkMarshInfo
return (UINT32)offsetof(UMThunkMarshInfo, m_pILStub);
}

#ifdef _TARGET_X86_
#if defined(_TARGET_X86_) && !defined(FEATURE_STUBS_AS_IL)
// Compiles an unmanaged to managed thunk for the given signature. The thunk
// will call the stub or, if fNoStub == TRUE, directly the managed target.
Stub *CompileNExportThunk(LoaderHeap *pLoaderHeap, PInvokeStaticSigInfo* pSigInfo, MetaSig *pMetaSig, BOOL fNoStub);
#endif // _TARGET_X86_
#endif // _TARGET_X86_ && !FEATURE_STUBS_AS_IL

private:
PCODE m_pILStub; // IL stub for marshaling
// On x86, NULL for no-marshal signatures
// On non-x86, the managed entrypoint for no-delegate no-marshal signatures
UINT32 m_cbActualArgSize; // caches m_pSig.SizeOfFrameArgumentArray()
#ifdef _TARGET_X86_
#if defined(_TARGET_X86_) && !defined(FEATURE_STUBS_AS_IL)
Stub* m_pExecStub; // UMEntryThunk jumps directly here
UINT16 m_cbRetPop; // stack bytes popped by callee (for UpdateRegDisplay)
UINT16 m_callConv; // unmanaged calling convention and flags (CorPinvokeMap)
Expand Down Expand Up @@ -248,7 +248,7 @@ class UMEntryThunk
static UMEntryThunk* CreateUMEntryThunk();
static VOID FreeUMEntryThunk(UMEntryThunk* p);

#ifdef _TARGET_X86_
#if defined(_TARGET_X86_) && !defined(FEATURE_STUBS_AS_IL)
// Compiles an unmanaged to managed thunk with the given calling convention adaptation.
// - psrcofsregs are stack offsets that should be loaded to argument registers (ECX, EDX)
// - psrcofs are stack offsets that should be repushed for the managed target
Expand All @@ -263,7 +263,7 @@ class UMEntryThunk
UINT *psrcofsregs,
UINT *psrcofs,
UINT retbufofs);
#endif // _TARGET_X86_
#endif // _TARGET_X86_ && !FEATURE_STUBS_AS_IL

#ifndef DACCESS_COMPILE
VOID LoadTimeInit(PCODE pManagedTarget,
Expand Down Expand Up @@ -569,12 +569,12 @@ class UMEntryThunkCache
AppDomain *m_pDomain;
};

#ifdef _TARGET_X86_
#if defined(_TARGET_X86_) && !defined(FEATURE_STUBS_AS_IL)
//-------------------------------------------------------------------------
// One-time creation of special prestub to initialize UMEntryThunks.
//-------------------------------------------------------------------------
Stub *GenerateUMThunkPrestub();
#endif // _TARGET_X86_
#endif // _TARGET_X86_ && !FEATURE_STUBS_AS_IL

//-------------------------------------------------------------------------
// NExport stub
Expand Down
7 changes: 2 additions & 5 deletions src/vm/i386/cgenx86.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -760,6 +760,7 @@ WORD GetUnpatchedCodeData(LPCBYTE pAddr)

#ifndef DACCESS_COMPILE

#if defined(_TARGET_X86_) && !defined(FEATURE_STUBS_AS_IL)
//-------------------------------------------------------------------------
// One-time creation of special prestub to initialize UMEntryThunks.
//-------------------------------------------------------------------------
Expand All @@ -772,7 +773,6 @@ Stub *GenerateUMThunkPrestub()
}
CONTRACT_END;

#ifndef FEATURE_STUBS_AS_IL
CPUSTUBLINKER sl;
CPUSTUBLINKER *psl = &sl;

Expand Down Expand Up @@ -809,11 +809,8 @@ Stub *GenerateUMThunkPrestub()
psl->EmitComMethodStubEpilog(UMThkCallFrame::GetMethodFrameVPtr(), rgRareLabels, rgRejoinLabels, FALSE /*Don't profile*/);

RETURN psl->Link(SystemDomain::GetGlobalLoaderAllocator()->GetExecutableHeap());
#else // FEATURE_STUBS_AS_IL
PORTABILITY_ASSERT("GenerateUMThunkPrestub");
return NULL;
#endif // FEATURE_STUBS_AS_IL
}
#endif // _TARGET_X86_ && !FEATURE_STUBS_AS_IL

Stub *GenerateInitPInvokeFrameHelper()
{
Expand Down
32 changes: 32 additions & 0 deletions src/vm/i386/umthunkstub.S
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
// Licensed to the .NET Foundation under one or more agreements.
// The .NET Foundation licenses this file to you under the MIT license.
// See the LICENSE file in the project root for more information.

.intel_syntax noprefix
#include "unixasmmacros.inc"
#include "asmconstants.h"

//
// eax = UMEntryThunk*
//
NESTED_ENTRY TheUMEntryPrestub, _TEXT, UnhandledExceptionHandlerUnix
// Preserve argument registers
push ecx
push edx

push eax
call C_FUNC(TheUMEntryPrestubWorker)
pop edx

// Restore argument registers
pop edx
pop ecx

jmp eax // Tail Jmp
NESTED_END TheUMEntryPrestub, _TEXT


NESTED_ENTRY UMThunkStub, _TEXT, UnhandledExceptionHandlerUnix
int 3 // implement here
ret
NESTED_END UMThunkStub, _TEXT
14 changes: 7 additions & 7 deletions src/vm/prestub.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1647,9 +1647,9 @@ PCODE MethodDesc::DoPrestub(MethodTable *pDispatchingMT)
// use the prestub.
//==========================================================================

#ifdef _TARGET_X86_
#if defined(_TARGET_X86_) && !defined(FEATURE_STUBS_AS_IL)
static PCODE g_UMThunkPreStub;
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

How about using FEATURE_STUBS_AS_IL instead of FEATURE_PAL?

#endif // _TARGET_X86_
#endif // _TARGET_X86_ && !FEATURE_STUBS_AS_IL

#ifndef DACCESS_COMPILE

Expand All @@ -1676,9 +1676,9 @@ void InitPreStubManager(void)
return;
}

#ifdef _TARGET_X86_
#if defined(_TARGET_X86_) && !defined(FEATURE_STUBS_AS_IL)
g_UMThunkPreStub = GenerateUMThunkPrestub()->GetEntryPoint();
#endif // _TARGET_X86_
#endif // _TARGET_X86_ && !FEATURE_STUBS_AS_IL

ThePreStubManager::Init();
}
Expand All @@ -1687,11 +1687,11 @@ PCODE TheUMThunkPreStub()
{
LIMITED_METHOD_CONTRACT;

#ifdef _TARGET_X86_
#if defined(_TARGET_X86_) && !defined(FEATURE_STUBS_AS_IL)
return g_UMThunkPreStub;
#else // _TARGET_X86_
#else // _TARGET_X86_ && !FEATURE_STUBS_AS_IL
return GetEEFuncEntryPoint(TheUMEntryPrestub);
#endif // _TARGET_X86_
#endif // _TARGET_X86_ && !FEATURE_STUBS_AS_IL
}

PCODE TheVarargNDirectStub(BOOL hasRetBuffArg)
Expand Down