systemprogramming 5

[메모리관리] 전방선언 잘 사용하기

전방선언을 사용하는 이유는 많지만 원리는 일단 선언해놓고 돌아가게하고 실행시에 전방선언된 것의 전체 정의를 가져다가 쓰겠다 라는 의미이다. 보통 헤더파일에 불필요하게 #include말고 cpp파일에 #include해서 코드 수 자체를 줄이려는 의도로 많이쓰인다.그런데 예를들어 다음과 같이 그런의도가 아닌경우도 있다.class Animation;struct MeshDataInfo { MeshData* meshes = nullptr; UINT meshCount = 0; Animation* m_animations = nullptr; UINT animationCnt = 0;.. Animation*이거 하나를 넣으려고 #include "Animation.h"하기에는 좀 치졸하다. 그래서 전방선언 했..

[매크로 충돌 제거] 디버깅누수 new 매크로와, Assimp new매크로

메모리 leak이 났을 때 출력창에Detected memory leaks!Dumping objects ->C:\Users\Lenovo\source\repos\Dx12Engine\Dx12Engine\Renderer.cpp(398) : {257} normal block at 0x000001CFFEC93A20, 592 bytes long. Data: 02 00 00 00 00 00 00 00 CD CD CD CD CD CD CD CD Object dump complete.The program '[10252] Dx12Engine.exe' has exited with code 0 (0x0). 이렇게 코드 몇번째 줄 어디서 에러가 떴는지 출력해주기 위해선#ifdef _DEBUG#define new new(_NOR..

[lib,dll] 외부 라이브러리(Assimp)이용 시 lib와 dll개념

Assimp를 사용할 때 vcpkg를 사용하지 않고, 소스를 CMake로 받아서 사용해봤다. Assimp.sln이 있는데, 이걸 Visual Studio에서 빌드 솔루션 하면 포함된 헤더와 cpp 파일들을 잘 엮어서 lib와 dll 파일을 생성한다. 여기서 생성된 lib와 dll 파일을 내 엔진에 넣어 사용해야 한다. lib 파일은 내 엔진 소스코드가 있는 폴더(헤더와 cpp 등)에 넣으면 되고, dll 파일은 exe 파일이 있는 위치에 넣으면 된다. dll파일을 엔진 소스코드가 들어있는 폴더에 넣을 필요가 없는것은, dll은 완성된 실행파일에서 가져다가 사용하는 개념이기 때문이다. 둘의 개념을 잘 구분하는게 도움이 되니 다음과 같이 정리하였다. 1) lib(Library,*lib)빌드 시점에 링커가 l..

[c++] 상호참조 아니더라도 전방선언 해줘야 하는 이유

cpp에서 서로 상호참조 할 경우, 둘다 완전히 정의되기전에 서로 참조를 하니 순환참조가 일어나 컴파일이 되지 않는다. 그 때 전방선언을 하는데 상호참조가 아니더라도 다른 헤더파일의 클래스를 가져다가 쓸 때는 전방선언을 해주는 것이 안전하다. 예를들어보자, winapp.cpp에 #include "renderer.h"을 했다. 그런데 renderer.h의 class에는 DescriptorPool* m_descriptorPool;이 있다. 이 때, renderer.cpp에서만 #include "DescriptorPool"하고 #include "renderer.h"만 한다고 해서 끝난게 아니다. winapp.cpp에서 renderer.h을 포함시킬 때, DescriptorPool이 어디서 왔는지 경우를 모를..

[System] 헤더파일에 정의를 하면 안되는 이유 + inline처리

보통 헤더파일에 함수를 선언만하고 정의는 따로 cpp에서 한다. 그렇게 하지 않으면 링커 단계에서 오류가 뜰 수 있다. 예를들어 다음과 같은 상황을 보자A.h 라는 헤더파일에 void FuncA() { ... } 처럼 함수 정의가 들어있다.B.cpp, C.cpp 모두 A.h 를 include한다. 그리고 디버깅을 해보자. B.obj파일이나 C.obj파일에 이미 함수A가 정의되어 있다고하는 오류가 뜰 것이다. 분명 나는 정의를 한 헤더파일에 한번만 했는데 왜 오류가 뜰까 원리를 생각해보면, 다음과같다. 컴파일러는 B.cpp 를 처리하면서 A.h의 FuncA 정의를 보고 B.obj 에 FuncA의 기계어 코드(정의)를 생성한다. 이와같이 C.cpp를 처리하면서 C.obj에 FuncA의 기계어 코드(정의)를 ..