Programing

NullReferenceException에 null에 대한 정보가 포함되지 않는 이유는 무엇입니까?

lottogame 2020. 11. 2. 07:35
반응형

NullReferenceException에 null에 대한 정보가 포함되지 않는 이유는 무엇입니까?


기본 클래스 데이터 (예 : 스택 추적)를 제외한 런타임 관련 정보를 포함하지 않는 NullReferenceException의 설계 결정은 무엇입니까? 그리고 식의 어느 부분이 null인지 바로 알 수있는 Visual Studio 용 확장이 있습니까?


NRE는 매우 낮은 수준의 예외입니다. 64K 미만의 주소에서 데이터를 읽으라는 요청을받을 때 프로세서가 생성하는 하드웨어 예외 ( '트랩')입니다. 가상 메모리 공간의 해당 영역은 특히 포인터 버그를 잡기 위해 항상 매핑 해제됩니다. AccessViolation으로 시작하여 주소가 0x00010000보다 작을 때 CLR에 의해 NRE로 전환됩니다. 이 시점에서 예외에 대한 컨텍스트는 거의 없으며 알려진 것은 트랩을 발생시킨 기계어 코드 명령어의 주소뿐입니다.

기계어 코드 명령 주소를 프로그램의 명명 된 변수로 역 엔지니어링하는 것은 불가능합니다. 그렇게 작동하는 것이 중요합니다 . 그렇지 않으면 지터가 매우 비효율적 인 코드 를 생성해야합니다 . 합리적으로 수행 할 수있는 모든 작업은 소스 코드 줄 번호를 복구하는 것입니다. 줄 번호 정보가 포함 된 디버깅 정보 (.pdb)가 필요합니다. CLR은 .pdb 파일을 읽는 방법을 알고 있으며이를 사용하여 예외의 스택 추적을 생성합니다. 그러나 이것은 JIT 최적화 프로그램이 수행하는 최적화로 인해 여전히 부정확 한 경우가 많으며 코드를 이동합니다. 디버그 빌드에 대한 보장 된 일치 만 얻을 수 있습니다. 릴리스 빌드 용 PDB에 소스 행 번호 정보가 포함되지 않은 이유입니다. 변경할 수 있습니다.

이 문제에는 매우 간단한 해결책이 있습니다. null을 직접 확인하고 런타임이 수행하도록하기 전에 자체 예외를 생성하십시오. 테스트는 매우 저렴하며 나노초보다 훨씬 적습니다.


NullReferenceExceptioncatch 블록에서 처음이 아니라 즉시 Throw에서 중단되도록 Visual Studio를 설정할 수 있습니다 .

  • 디버그
  • 예외
  • 공통 언어
  • 런타임 예외 시스템
  • System.NullReferenceException (확인란 선택)

그런 다음 NullReferenceException.


런타임에 null이 무엇인지 확인하는 사소한 방법은 없습니다. 필요한 정보는 IL에서 디 컴파일되고 유추되어야합니다. 이는 충분히 낮은 수준이므로 "스택 맨 위에있는 항목이 null입니다. "하지만 그 항목이 어떻게 거기에 도착했는지는 알 수 없습니다.

(그리고 나는 그러한 확장에 대해 모르지만 훌륭한 디버거 향상 이 될 것입니다 )


NullReferenceException언어가 아닌 런타임에 의해 발생합니다. 런타임은 참조가 어디에서 왔는지 알지 못합니다. 명령이 널 참조를 사용하려한다는 것만 알고 있습니다.

사실, 예외는 "아마도"네이티브 윈도우 "유효하지 않은 액세스 위반"SEH 예외의 결과이며, 이는 런타임에 의해 포착되어 IL 예외로 변환됩니다 ( "아마":이 경우인지 확인하지 않았지만 코드를 JIT하는 가장 성능이 좋은 방법이 무엇인지 내 추측입니다.)


코드에 대한 모든 정보를 런타임에 사용할 수있는 것은 아닙니다. 예를 들어 지역 변수 이름을 사용할 수 없습니다. 따라서 'local variable myObj is null but it 's member has been called'와 같은 메시지와 함께 예외를 던지는 것은 불가능합니다. 또한 런타임에 사용자가 작성하지 않은 객체 (예 : 클로저 / 익명 유형 / 반복자 등을 위해 생성 된 클래스)가 많이 있으며 이는 null-ref 예외의 소스가 될 수도 있습니다.


디버그 기호가있는 경우 예외를 발생시킨 줄을 추적 할 수 있습니다. 충분히 간단하다면 null가치를 곧바로 얻을 수 있습니다. 그렇지 않으면 (생각해보십시오 a.Value = b.Do(c.GetX(),d.GetY(z.ToString()));) IDE로 디버그해야합니다.

참고 URL : https://stackoverflow.com/questions/4719047/why-doesnt-nullreferenceexception-contain-information-about-what-is-null

반응형