2016-05-31 2 views
9

나는 C#에서 작업해온 애드온 안에 두 가지 다른 기능을 가지고 있습니다. 최근에 (분명히) SolidWorks는이 두 함수의 특정 부분에 도달하면 충돌이 발생했습니다 (이보다 더 많을 수는 있지만 지금까지 발생한 것으로 나타났습니다). 디버그에서 두 함수 모두 "메모리 액세스 위반 오류". 이 오류는 매번 활성 문서를 닫고있는 선에서 발생하며 시간의 약 95 %가 발생합니다.솔리드 웍스, Isldworks.CloseDoc의 메모리 액세스 위반 오류를 추적

거의 항상 같은 부분에 있습니다. 실행 시간이나 열리고 닫힌 부분의 수와는 별개의 것으로 보입니다. 파일을 닫지 않으면 오류가 발생하지 않습니다. 그러나 대규모 어셈블리를 실행하면 자체 문제가 발생합니다. 닫기 전에 1 초 대기 시간을 추가하면 오류 빈도가 줄어들는 것처럼 보입니다 (오류없이 전체 어셈블리를 가끔씩 볼 수 있음)

내가 주로 염려하는 기능에 대한 간단한 설명 ; 어셈블리의 최상위 수준에서 작동하여 주 어셈블리 및 하위 어셈블리의 사용자 지정 속성을 자식으로 전파합니다. 그래서 저는 계속해서 다른 어셈블리와 파트 파일을 열고 닫고 있습니다.

아래의 코드는 오류를 복제하는 최소한의 것으로 거의 제거되었습니다. 오류는 59 번 줄에서 발생합니다. 지금까지 온라인에서 본 Ive에서 추적하기가 어려워 보입니다. 어떤 도움이라도 대단히 감사합니다.

public void propagateProps(bool overwrite) 
    { 
     List<string> assemblies = new List<string>(); 
     string topAssem; 
     string compName = ""; 
     int i = 0; 
     int j = 0; 
     int errors = 0, warnings = 0; 
     int partType = 1; 
     swModel = iSwApp.ActiveDoc; 
     if (swModel == null) 
     { 
      MessageBox.Show("No assembly document open. Please open an assembly and try again.", "Avengers Assemble Error"); 
      return; 
     } 
     if (swModel.GetType() != 2) 
     { 
      MessageBox.Show("No assembly document open. Please open an assembly and try again.", "Avengers Assemble Error."); 
      return; 
     } 
     topAssem = swModel.GetPathName(); 
     assemblies.Add(swModel.GetPathName()); 
     swAssy = iSwApp.ActiveDoc; 
     while (i < assemblies.Count) 
     { 
      List<string> beenDone = new List<string>(); 
      iSwApp.OpenDoc(assemblies[i], 2); 
      swModel = iSwApp.ActivateDoc(assemblies[i]);     
      swAssy = iSwApp.ActiveDoc; 
      foreach (Component2 swComp in swAssy.GetComponents(true)) 
      { 
       partType = 1; 
       compName = swComp.GetPathName(); 
       if (compName.IndexOf(").SLD") > 0 || compName.IndexOf("REF") > 0) 
       { 
        continue; 
       } 
       if (Path.GetExtension(compName).ToUpper() == ".SLDASM") 
       { 
        partType = 2; 
        assemblies.Add(compName); 
       } 
       iSwApp.OpenDoc(compName, partType); 
       swModel = iSwApp.ActivateDoc(compName); 
       if (swModel == null) 
       { 
        continue; 
       } 


       #region things that might not be in 


      #endregion 


       boolstatus = swModel.Save3(5, errors, warnings); 
       System.Threading.Thread.Sleep(500); 
       iSwApp.CloseDoc(swModel.GetPathName()); 
      swPart = null; 
      swModel = null; 
      } 
      ++i; 
      System.Threading.Thread.Sleep(500); 
     } 


     return; 
    } 

업데이트 :이 질문을보고 나면; What's causing the memory access violation? 필자는 필자의 함수에서 아무런 영향을 미치지 않는 일부 전역 변수를 사용하려고했습니다. 그러나 나는이 논점을 피하는 것처럼 보이는 부분을 반복하면서 다른 논리적 구조로 내 핵심 코드를 래핑 할 수 있었다. 그러나 나는 기껏해야 반창고를 느낀다. 그리고 앞으로이 문제를 피할 수 있기를 바란다.

+0

아무도 입력하지 않았습니다. – Nick

+1

C#에서 코드를 작성 중입니다. PInvokes, 안전하지 않은 블록 또는 이와 유사한 방식으로 작업하지 않는 한 메모리 액세스 예외를 일으킬 수 없습니다. 합리적인 유일한 대답은 SolidWorks가 합당한 입력을 충돌하게 만들거나 부당한 입력을 확인하지 못하기 때문에 충돌을 일으키는 버그가 있다는 것입니다. 아무데도 어디에서 건가요? 닫은 후에 개체를 사용하려고합니까? 비동기식 작업을 사용하고 있습니까? 당신은 어떤 고리를 제공하고 있습니까? – antiduh

+0

[OpenDoc] (http://help.solidworks.com/2012/English/api/sldworksapi/SolidWorks.Interop.sldworks~SolidWorks.Interop.sldworks.ISldWorks~OpenDoc.html)은 더 이상 사용되지 않습니다. 새로운 방법을 사용하지 않는 이유는 무엇입니까? OpenDoc의 반환 값을 사용하지 않는 이유는 무엇입니까? – antiduh

답변

4

당신은 PInvokes, 안전하지 않은 블록 또는 유사하게 작업하지 않는 한, 메모리 액세스 예외를 일으킬 수 없어야합니다. 합리적인 유일한 대답은 SolidWorks가 합당한 입력을 충돌하게 만들거나 부당한 입력을 확인하지 못하기 때문에 충돌을 일으키는 버그가 있다는 것입니다.

실제 수정은 SolidWorks에 연락하여 버그를 재생산하고 수정하는 것입니다. 이를 제외하고는 버그와 결함의 일반적인 트리거 인 상호 작용을 찾기 위해 코드를 분석 할 수 있습니다. 예를 들어, 모든 입력을 올바르게 검증하지 못할 수도 있습니다. 자동으로 승인하는 잘못된 값을 제공 할 수 있습니다. 나중에는별로 깨지 않습니다.

실수로 널 (NULL)을 전달하고 점검하지 않은 경우 나중에 널 (null)에서 포인터를 가져 오면 메모리 액세스 위]이 발생할 수 있습니다. 리소스를 닫은 후에 리소스를 사용하고 있고 이러한 조건에 대해 유효성을 검사하지 않은 경우 후드 아래에 부실 포인터가 사용되어 메모리 액세스 위반이 발생할 수 있습니다.

비동기 작업으로 인해 일부 비동기 작업이 시작된 다음 해당 작업과 연결된 리소스를 닫으면 나중에 해당 작업이 백그라운드에서 진행될 때 오류가 발생할 수 있습니다.

핸들을 사용하는 방식이 메모리 액세스 위반을 일으킬 수 있습니다. OpenDoc의 반환 값을 사용하지 않고 다른 방법으로 문서에 액세스하려고합니다. OpenDoc의 반환 값이 가비지 수집되면 어떻게됩니까?어쩌면 SolidWorks가 제대로 계산되지 않아 반환 값이 GC 일 때 후드 아래의 핸들이 닫히고 없어진 것일 수 있습니다. 아직 다른 연산은 여전히 ​​유효 할 것으로 기대하므로 메모리 액세스 위반이 발생합니다.

더 이상 사용되지 않는 API를 사용하고있을 수도 있습니다. 그렇다면 더 이상 테스트하거나 유지 관리하지 않으므로 버그가 발생할 확률이 높은 SolidWorks 코드를 사용 중일 수 있습니다. 해당 설명서가 사용되지 않는 것으로 나열된 OpenDoc 메서드를 호출하는 것으로 나타났습니다. 대신 권장되는 방법 (예 : OpenDoc6)을 사용하는 것이 좋습니다.

API의 실제 문제가 깨진 경우 또는 깨진 입력에 대해 유효성을 검사하지 않는 경우 유일한 해결책은 이러한 일반적인 API 문제의 원인을 조사하는 것입니다.

+1

위에서 말했듯이 OpenDoc6 호출을 사용하면 실제로 다른 문제가 발생할 수 있으므로 결국 문제가 해결 된 것 같습니다. 고맙습니다! – Nick

관련 문제