문제
변수에 대한 포인터가 주어지면 .. 정적으로 또는 동적으로 할당되었는지 확인하는 방법이 있습니까?
해결책
귀하의 의견에서 인용 :
기본적으로 구조물을 제거하는 방법을 만들고 있습니다. 그것은 malloced 일 수도 있고 아닐 수도있는 것에 대한 포인터 인 데이터 멤버가 있습니다. 어떤 것에 따라, 나는 그것을 자유롭게하고 싶습니다.
올바른 방법은 추가하는 것입니다 또 다른 구조물 멤버 : 거래 기능에 대한 포인터.
정적 대 동적 할당만이 아닙니다. 거기 있습니다 몇몇의 가능한 할당 자 malloc()
단지 하나 일뿐입니다.
유닉스와 같은 시스템에서는 다음과 같습니다.
- 정적 변수
- 스택에
- 스택에서는 동적으로 할당되지만 (즉
alloca()
) - 힙에 할당되었습니다
malloc()
- 힙에 할당되었습니다
new
- 힙에
new[]
- 힙에, 구조물 내에서
malloc()
- 힙에
new
- 할당되었습니다
mmap
- 사용자 정의 할당자를 할당합니다
- 위의 몇 가지 조합 및 변형을 포함하여 더 많은 옵션
Windows에는 여러 개의 런타임이 있습니다. LocalAlloc
, GlobalAlloc
, HeapAlloc
(쉽게 만들 수있는 몇 가지 힙으로) 등.
사용한 할당 자의 올바른 릴리스 기능으로 항상 메모리를 해제해야합니다. 따라서 메모리 할당을 담당하는 프로그램의 일부는 메모리를 제거해야하거나 메모리를 제거 할 코드로 올바른 릴리스 기능 (또는 주변 래퍼)을 전달해야합니다.
또한 포인터가 항상 특정 할당 자와 함께 할당되도록하거나 할당자를 직접 제공하여 전체 문제를 피할 수 있습니다 (메모리를 할당하는 기능의 형태와 그 기능을 해제 할 수있는 함수). 할당자를 직접 제공하는 경우 (태그 포인터와 같은) 트릭을 사용하여 정적 할당을 사용할 수 있습니다 (그러나 여기서는이 접근법의 세부 사항을 사용하지 않습니다).
레이몬드 첸 그것에 대한 블로그 게시물이 있습니다 (Windows 중심이지만 개념은 어디에서나 동일합니다) : 모듈 경계를 통해 메모리 할당 및 자유화
다른 팁
그만큼 에이스 도서관은 모든 곳 에서이 작업을 수행합니다. 그들이 어떻게하는지 확인할 수 있습니다. 일반적으로 당신은 아마도 처음에 이것을 할 필요가 없을 것입니다 ...
힙, 스택 및 정적 데이터 영역은 일반적으로 다른 메모리 범위를 차지하기 때문에 프로세스 메모리 맵에 대한 친밀한 지식으로 주소를보고 어떤 할당 영역이 있는지 결정하는 것이 가능합니다.이 기술은 두 아키텍처입니다. 컴파일러에 따라 코드를 포팅하기가 더 어려워집니다.
대부분의 LIBC Malloc 구현은 블록의 크기에 대한 정보와 '마법'값에 대한 정보를 갖는 필드 (Free () 호출에서 사용하기 위해)가있는 각 반환 된 메모리 블록 앞에 헤더를 저장하여 작동합니다. 이 마법의 가치는 사용자가 실수로 할당되지 않은 포인터를 삭제하는 사용자로부터 보호하는 것입니다 (또는 사용자가 덮어 쓰인 블록을 해제). 그것은 매우 시스템에 따라 다르므로 LIBC 라이브러리의 구현을보고 마법의 가치가 정확히 있는지 확인해야합니다.
이 사실을 알게되면 주어진 포인터를 헤더의 포인트로 다시 이동 한 다음 마법의 가치를 확인하십시오.
Malloc Debuggers와 마찬가지로 ld_preload 등을 사용하여 Malloc () 자체에 연결할 수 있습니까? 그렇다면 할당 된 모든 포인터의 테이블을 유지하고 사용할 수 있습니다. 그렇지 않으면 확실하지 않습니다. Malloc의 부기 정보를 얻는 방법이 있습니까?
표준 기능이 아닙니다.
Malloc 라이브러리의 디버그 버전에는이를 수행 할 수있는 기능이있을 수 있습니다.
주소를 정적으로 알고있는 것과 비교할 수 있으며, 멀리 떨어져있는 경우에만 말을 걸고 있다고 말할 수 있습니다. 범위를 알고 있다면 그 범위가 알려지지 않은 경우 실제로 믿을 수 없습니다.
1.) 보유한 코드에 대한 맵 파일을 얻습니다.
2.) 기본 프로세스/하드웨어 대상 플랫폼에는 일반적으로 메모리의 시작 주소 (스택, 힙, 글로벌 0, 해당 블록의 크기, 해당 메모리 블록의 읽기 쓰기 속성을 나타내는 메모리 맵 파일이 있어야합니다.
3.) 1의 MAO 파일에서 객체 (포인터 변수)의 주소를 얻은 후) 주소가 어떤 블록에 떨어지는 지 확인하십시오. 당신은 아이디어를 얻을 수 있습니다.
= AD