2013-09-26 5 views
1

타사 코드를 호출하는 C++/CLI 래퍼를 만들었습니다.이 코드는 손상된 메모리에서 종료되었습니다.이것은 C++에서 합법적입니까?

void Init_4bit_tab(unsigned char *dest,unsigned char *source) 
     { 
      unsigned char masque,i; 

      masque=0x08; 
      for(i=0; i<4; i++) { 
       dest[i] = (*source & masque)>>(3-i); 
       masque >>= 1; 
      } 
     } 

정확한 오류가 있었다 : 보호 된 메모리를 읽거나 쓰려고 시도 그래서 아마 코드가 C에서 불법이라고 의심하고있어 ++

아래 추락 코드입니다. 이것은 종종 다른 메모리가 손상되었다는 표시입니다.

업데이트 : 제 3 자 코드를 스캔 한 후

는, 그것 때문에 전달 방식, 다차원 배열로 나타납니다,하지만, 난 여전히 문제의 원인 모르겠어요 :

소스를 기능

unsigned char Data_B[81]; 
... 
S_Box_Calc(&Data_B[33]); 

void S_Box_Calc(unsigned char *vect) 
     { 
       unsigned char *S_Box[8]; 
       unsigned lig,col,i; 

       S_Box[0]=S1; 
       S_Box[1]=S2; 
       S_Box[2]=S3; 
       S_Box[3]=S4; 
       S_Box[4]=S5; 
       S_Box[5]=S6; 
       S_Box[6]=S7; 
       S_Box[7]=S8; 

       for(i=0;i<8;i++) { 
        col= 8*vect[1+6*i] + 4*vect[2+6*i] + 2*vect[3+6*i] + vect[4+6*i]; 
        lig= 2*vect[6*i] + vect[5+6*i]; 
        Init_4bit_tab(&vect[4*i],&S_Box[i][col+lig*16]); 
       } 
     } 

업데이트 2 : 가 나는 이명 령과 소스가 null없는 디버그 모드에서 값을 확인. 그러나이 코드 아래에서 빠른 시계 (* 소스 & 가면극)를 시도한 경우 dest [i] = (* 소스 & 가면극) >> (3-i);

는이 오류를

(* 소스 & 가면극) 오류가 발생합니다 : S1 ... Sn을 원래의 정의 : &는 '* 소스'와 '가면극'

업데이트 3을 수행 할 수 없습니다 파일의 전역,하지만 난있는 그대로를 떠날 때 오류가 발생합니다, 그래서 생성자에서이 방법을 초기화 :

unsigned char lS1[64] = { 
       14,4,13,1,2,15,11,8,3,10,6,12,5,9,0,7, 
       0,15,7,4,14,2,13,1,10,6,12,11,9,5,3,8, 
       4,1,14,8,13,6,2,11,15,12,9,7,3,10,5,0, 
       15,12,8,2,4,9,1,7,5,11,3,14,10,0,6,13 
      }; 
      std::copy(S1, S1 + 64, lS1); 

이 문제가 될 수 있습니까?

+1

'dest'가 가리키는 메모리와 비슷한 소리가 유효하지 않거나 충분히 크다. –

+1

source = nullptr도 충돌을 일으킬 수 있습니다. –

+0

'S1', 'S2' 등의 선언/정의는 무엇입니까? – legends2k

답변

0

표시된 코드에 아무런 문제가 없습니다. 이면에 유효한 포인터가 전달됩니다. 메모리가 손상된 경우 호출자가 올바른 포인터를 전달하지 않았으므로 아마도 일 것입니다. 편집 한 후

: 당신이 보여로 S_Box_CalcData_B + 33에 동일한 vect 호출되는 경우, 범위 [vect, vect+48)는 에, Init_4bit_tab는 사실 (44)에 우수한 값이 호출 할 수 없습니다 것을 의미하는 법률 표시되는 코드는 이 28보다 큰 값으로 호출되지 않으므로 에서 메모리를 손상시킬 수 없어야합니다. 그러나 S1에서 S8 사이에있는 경우 이 유효한 메모리를 나타내지 않으면 상태라는 증상이 나타납니다.

+0

편집 3에서 std :: copy 후 생성자를 살펴 보았습니다. lSn이 Sn에 올바르게 복사되지 않았고 대신 모두 0xcd 문자가되었습니다. – user2817517

0

이것은 완벽하게 합법적 인 C++ 구문 적으로 컴파일 된 것입니다. 의미 론적으로 올바른지 확인하십시오. 실수로 UB 랜드를 밟을 수있는 유일한 곳은 dest 포인터입니다. 즉, 포인터가 가리키는 배열은 포인터가 가리키는 곳에서 4 칸 이상 떨어져 있어야합니다. 또한 오류가 액세스 위반에 대해 말한 이후 dest이 쓰기 가능한 메모리 위치를 가리키고 있는지 확인하십시오.

+0

내 코드 – user2817517

+1

"Legal C++"! = "C++ 컴파일"을 업데이트했습니다. "정의되지 않은 동작"은 컴파일러가 감지 할 수있는 규칙을 위반하지 않는 불법 프로그램이있을 때 발생합니다. –

+0

@SebastianRedl : C++ 표준 :'C++에서 정적 또는 extern 지정자는 객체 또는 함수의 이름에만 적용 할 수 있습니다. 타입 선언과 함께 이러한 지정자를 사용하는 것은 C++에서 _illegal_입니다. 즉 컴파일러에서 오류가 발생합니다. – legends2k

0

오버플로 확인은 어디에 있습니까? 오버플로 될 가능성이있는 경우 메모리로 쓰기를 제한 할 수 있도록 함수에 크기를 전달해야합니다. strcpy()와 비슷합니다.BSD의 strncpy() 또는 strlcpy(). 아마도 이러한 라인을 따라 무언가를 구현하고, 그렇지 않으면 메모리가 흘러 넘치게되는 조건이있는 경우 오류를 생성하면 메모리 손상의 원인을 발견 할 수 있습니다.

관련 문제