Friday 16 March 2018

그물 마셜 gethrforexception


marshal. gethrforexception
App Store를 통해 가져 오기 우리의 응용 프로그램 에서이 게시물을 읽으십시오!
부분 신뢰 환경에서 Marshal. GetHRForException 호출 (SecurityPermission)
try..catch 내에서 스트림을 읽는 IO 코드가 있습니다. IOException을 포착하고 HResult를 기반으로 다른 조치를 취하기 위해 catch 내에서 System. Runtime. InteropServices. Marshal. GetHRForException ()을 호출합니다. 이 같은:
그러나이 코드를 ASP 내에서 trust = "medium"으로 실행하면이 예외가 발생합니다.
몇 가지 질문 :
GetHRForException은 중간 트러스트에서 허용되지 않는 비 관리 코드를 호출하기 때문에 예외가 발생한다고 생각합니다. 옳은? 이 예외는 Throw되고 GetHRForException의 실행 시점이 아니고 메소드가 JIT 될 때 - 올바른가? (stacktrace 내 방법을 보여줍니다, 하지만 나는 IO 예외가 발생하지 않은 99 % 확실) 그렇다면 내가 GetHRForException을 호출하지 않도록 부분 신뢰 환경에서 동작을 다양하게하는 방법이 있습니까 관리되지 않는 코드) 어디에서 허용되지 않습니까? 즉, JIT가 컴파일 타임에 성공하도록 허용하면서 런타임에 코드가 GetHRForException ()을 호출해야하는지 여부를 평가할 수 있습니까? 이 같은:
사용 권한을 사용할 수 있는지 테스트 할 런타임 메커니즘이 있다고 생각하지만 찾을 수는 없습니다.

marshal. gethrforexception
App Store를 통해 가져 오기 우리의 응용 프로그램 에서이 게시물을 읽으십시오!
System. IO. IOException에 대한 HResult는 어떻게 결정합니까?
System. Exception. HResult 속성은 보호되어 있습니다. 어떻게하면 예외를 들여다 볼 수 있고 반영이나 다른 추악한 해킹에 의존하지 않고 HResult를 얻을 수 있습니까?
상황은 다음과 같습니다.
시스템에서 파일을 열고 읽는 백업 도구를 작성하려고합니다. 이 지침에 따라 FileAccess. Read 및 FileShare. ReadWrite를 사용하여 파일을 엽니 다. 파일을 읽었을 때 파일이 열려 있는지 여부가 신경 쓰이지 않기 때문입니다.
경우에 따라 읽는 파일이 다른 응용 프로그램에서 열리면 System. IO. FileStream. Read () 메서드가 System. IO. IOException을 throw합니다. "다른 프로세스가 일부 파일을 잠 갔기 때문에 프로세스가 파일에 액세스 할 수 없습니다. 파일". 이것은 오류 33이거나 HResult 0x80070021입니다. [편집 : 다른 프로세스가 파일 내의 바이트 범위를 잠그기 위해 LockFileEx를 호출 할 때 이것이 반환 될 수 있다고 생각합니다.]
이 오류가 발생하면 일시 중지하고 다시 시도하고 싶습니다. 나는 이것이 이것이 여기서 취하는 적절한 행동이라고 생각한다. 잠금 프로세스가 바이트 범위 잠금을 신속하게 해제하면 파일을 계속 읽을 수 있습니다.
어떻게 이런 이유로 IOException을 구별 할 수 있습니까? 나는이 방법들을 생각할 수있다.
사적인 반사 - 그러고 싶지 않아. 퍼프가 악취를냅니다. Exception. ToString ()을 호출하고 문자열을 구문 분석하십시오. 해키 같은 느낌. i18n 버전에서는 작동하지 않습니다.
나는이 옵션들을 좋아하지 않는다. 더 깔끔하고 깨끗한 방법이 있습니까?
방금 검색 한 결과 System. Runtime. InteropServices. Marshal. GetHRForException이 발견되었습니다. 그게 0x80070021 같은 uint를 반환할까요?
Framework 4.5 이상에서는 Exception. HResult 속성을 사용할 수 있습니다.
가치가있는 경우, System. Exception. HResult는 더 이상 4.5에서 보호되지 않습니다. setter만이 보호됩니다. 이는 하나 이상의 프레임 워크 버전으로 컴파일 될 수있는 코드에는 도움이되지 않습니다.
ISerializable 인터페이스를 사용할 수도 있습니다.
이 경우 CanRead 속성이 도움이됩니까?
즉 CanRead를 호출하면 true를 반환하면 Read ()를 호출합니다.
이 사건들 중 하나를 프로파일하셨습니까? 리플렉션 방법이 느린 것은 아니며, 특히 앱이 수행하는 다른 모든 작업과 관련이 있으며, 이 예외가 발생할 가능성이 얼마나 높은지에 대해 생각합니다.
병목 현상이 발생하면 리플렉션 연산을 캐싱하거나 동적 IL을 생성하여 속성을 검색 할 수 있습니다.

marshal. gethrforexception
메서드 외부에 예외가 전파되도록 허용하면 잘못된 동작이 발생합니다. 실제로 공용 언어 런타임은 v-table을 통해 이러한 메서드를 호출하는 COM 클라이언트에 예외를 전달하지 못합니다.
모든 PreserveSig 특성을 모든 인터페이스 메서드에서 제거하고 내 라이브러리에 대해 완전히 예외 기반 방식으로 이동 했으므로이 방법이 좋지 않습니다. 내 COM 개체에서 & quot; throw & quot; 호출자에게 오류를 되돌려 보낼 때마다 (관리되는 것과 관리되지 않는 것 모두) 나는 아직 문제를 보지 못했습니다. 나는 COMException을 던지고 HRESULT는 호출자의 hr에서 끝납니다. 게다가 (관리되지 않는) 클라이언트는 IErrorInfo 인터페이스를 검색하여 오류 코드와 함께 throw하는 텍스트를 수신 할 수 있습니다.
기존 문서가 현재 동작을 반영하도록 업데이트되지 않았습니까? 어쩌면 내가 말하려고하는 것을 오해하고있는 것일까 요? 아니면 저를 물으려고 기다리는 끔찍한 잡화가 있습니까?
모든 답장.
귀하의 정보가 유효 기간을 초과 할 수 있습니까? 나는 당신이 묘사하고있는 끔찍한 결과를 보려고 노력했지만, 그것은 단지 일어나지 않고 있습니다. 다음은 내 C ++ 프로그램입니다.
hr = CoCreateInstance (stype, NULL, CLSCTX_INPROC_SERVER, IID_IMFTransform, (void **) & amp; it);
다음은 DeleteInputStream의 코드입니다.
공공 무효의 DeleteInputStream (int dwStreamID)
새 COMException을 throw합니다 (& quot; 지원되지 않는 스트림 제거 중 & quot;, E_NotImplemented).
C ++ 호출에서 얻은 HRESULT는 예상대로 E_NOTIMPL입니다. 나는 C ++ 설정을 방황했으며 & quot; Enable c ++ exceptions & quot; 나는 그것을 "아니오"로 설정했다. 아직도, 내가 예상했던 시간을 되찾았다. 적용 할 다른 것을 보지 못했습니다.
그리고 아니오, 나는 clr을 지원하는 C ++ 프로그램을 컴파일하지 않을 것입니다. 실제로, "커맨드 라인"의 내용은 다음과 같습니다. 창문:
/ Od / D "WIN32" / D "_DEBUG" / D "_CONSOLE" / D "_UNICODE" / D "UNICODE" / Gm / RTC1 / MDd / Fo "Debug \\" /Fd"Debug\vc80.pdb" / W3 / nologo / c / Wp64 / ZI / TP / errorReport : 프롬프트.
그냥 기본 컴파일 옵션. Vista에서 실행 중이지만 문제가되지 않는 것 같습니다.
어쩌면 이것이 시간이 지남에 따라 변한 것일까요? 또는 내가 꺼야하는 다른 C ++ 컴파일 옵션이 있습니까?
죄송합니다, 내가 사용하고있는 프레임 워크 버전을 추가 했어야합니다. 내 COM 개체를 등록하는 데 사용하는 명령 줄은 다음과 같습니다.
c : \ Windows \ Microsoft \ Framework \ v2.0.50727 \ regasm / tlb / codebase MFT_Grayscale. dll.
Ok, 나는 걱정했다. 나는 "SUCCEEDED"의 수백 줄을 꺼냈다. 수백 개의 메소드에서 PreserveSig를 삭제하고 코드를 삭제합니다. 그 모든 것을 되돌려 놓아야했다. 발굴.
내가 너를 이걸 지나게 해줘서 고마워.
Microsoft는 Msdn 웹 사이트에 대한 귀하의 의견을 이해하기 위해 온라인 설문 조사를 실시하고 있습니다. 참여를 선택하면 Msdn 웹 사이트를 탈퇴 할 때 온라인 설문 조사가 제공됩니다.

Yi Zhang의 MSDN 블로그 Yi Zhang 및 MSDN 블로그
CLR에 대한 모든 것 & # 8211; interop / WinRT / 및 기타 임의의 것들.
Marshal. GetHRForException은 Get-HR-For-Exception 이상을 수행합니다.
먼저 작은 코드 스 니펫을 살펴 보겠습니다.
이것은 완벽하게 좋아 보인다. 그렇지 않아. 이 API는 실제 이름이 잘못 지정되어 있으며 예외 객체에서 HR을 검색하는 것 이상의 기능을합니다. 이 API를 잘못 사용하면 틀린 예기치 않은 예외를 버리는 등 이상한 문제가 발생할 수 있습니다.
그렇다면 API는 실제로 무엇을합니까?
HRESULT를 반환하는 것 외에도이 함수는 현재 스레드 인 IErrorInfo 객체를 예외 객체로 설정합니다. 모든 스레드는 관련 IErrorInfo COM 개체를 가지며 기본값은 NULL입니다. 이 IErrorInfo 객체는 GetLastError () Win32 API 또는 errno C api와 같은 일종의 마지막 COM API 호출의 실패를 나타냅니다. IErrorInfo 개체에서 오류에 대한 자세한 정보를 제공하는 오류 설명, 도움말 파일 컨텍스트 등의 자세한 정보를 얻을 수 있습니다. IErrorInfo 객체를 예외 객체 (실제로 모든 관리 객체가 공유하는 예외 객체의 IErrorInfo 구현으로 설정)로 설정하면 COM 호출자에게 & quot; 이봐 요, 실패가 있습니다. 이 예외 객체입니다. , 당신은 단지 HR을 검색하기를 원한다면 분명히 나쁜 생각 인 "그것에 대해 뭔가를해야합니다."
많은 경우 COM 호출자 / 피 호출자가 IErrorInfo를 올바르게 처리하면이 사실을 알 수 없습니다. "정확하게", 그들은 기본적으로 COM IErrorInfo 프로토콜을 따르는 것을 의미합니다.
1. 호출자는 & quot; IErrorInfo를 지원합니다 & quot;라고 명시된 COM 인터페이스를 호출 할 때 현재 스레드에서 IErrorInfo를 사용합니다.
2. "I support IErrorInfo"라고하는 피 호출자 (COM 인터페이스를 구현 함)는 IErrorInfo를 클리어 / 세트하여 리턴해야한다. 이것은 GetLastError () / errno와 매우 비슷합니다. 맞습니까?
이 경우 스레드에서 잘못 설정된 IErrorInfo는 일반적으로 IErrorInfo를 지원하는 일부 인터페이스 구현으로 덮어 쓰거나 지우거나 무시됩니다.
그러나 필자가 설명한 프로토콜은 모든 COM 개발자가 실제로 잘 이해하지 못하기 때문에 COM 구성 요소가 "확실하게 모든 COM 인터페이스에서 IErrorInfo를 지원합니다."라고 말하는 경우를 종종 보았습니다. IErrorInfo를 모두 지우십시오. 그리고이 잘못 구현 된 COM 인터페이스의 호출자는 GetHRForException 호출에 의해 설정된 IErrorInfo를 사용하게되고 결국 오류가 있다고 생각하게됩니다. 예를 들어, 다음 시나리오를 고려해보십시오.

No comments:

Post a Comment