하 시발 내 입으로 이제 그만한다고 두번이나 그래놨는데 또 글 싸서 미안하다. 이젠 그만둔다는 얘기 하지 말아야겠어.


코세가 깝싸는게 배알이 꼴리기도 하고 곰곰히 생각해보니 문제를 해결할 방법이 생각나서 잠깐 시간내서 해봤다.


내가 계속 얘기했던 문제가 'vs 맘대로 memcpy로 코드를 치환해버린다는 것'이었는데, 생각해보니 컴파일러 intrinsic을 쓰면 지맘대로 치환하지 않을거란 생각이 들더라.


x86을 잘 몰라서 좀 고생했는데, 인텔 인트린식 가이드(링크)랑, MSDN에 x86 instrinsics list(링크) 뒤적거려가면서 좀 해봤더니 역시나 memcpy로 치환을 안하더라고?


대충 MMX랑 SSE 찍고 load랑 store랑 prefetch 정도면 컴파일러가 코드 생성하는것마냥 내가 직접 할 수 있겠다 싶어서 해봤다.


인트린식 써서 그런지 vs가 원래 그런지 loop unrolling을 안해주길래 대충 손으로 언롤링하고, gcc로 짜보고 나오는 인스트럭션 보고 해당 인스트럭션에 대응되는 인트린식 찾아보니까 다 있더라.


windows 10에 8기가 램, AMD FX(tm)-4100 Quad-Core Processor 3.60 GHz에서 테스트 했고, VS 2015 썼다.


dumpbin /disasm으로 오브젝트 뒤져봤을 때 memcpy로 치환되는 부분 없는것 확인했고, 그래서 이젠 진짜 aligned/unaligned access만 다른 코드가 됐어.


> start /realtime test.txt 10000000 1 3 1000 으로, 10메가씩 복사하는데 dest는 1바이트, src는 3바이트 misalign나게 1000번 돌렸다.


x86에서


std::memcpy         , 6156 ms, 0.213325 GiB/s

my_memcpy           , 2236 ms, 0.58731 GiB/s

my_memcpy_byte_only , 14712 ms, 0.0892622 GiB/s

my_memcpy_unaligned , 4429 ms, 0.296506 GiB/s



x64에서


std::memcpy         , 2186 ms, 4.2604 GiB/s

my_memcpy           , 2172 ms, 4.28786 GiB/s

my_memcpy_byte_only , 14636 ms, 0.636323 GiB/s

my_memcpy_unaligned , 4374 ms, 2.12922 GiB/s



x86으로 빌드하면 내 컴터가 이상한건지 퍼포먼스가 줮나게 떨어지는데 원인은 잘 모르겠지만 어쨌든 경향성은 보이니까 괜찮을 듯? x86에서는 vs의 memcpy보다도 빠르게 나오는데, vs memcpy 뜯어봐도 sse2 써가며 짜놨던데 왜 내꺼가 더 빠른지는 좀 의문.


x64에서는 std::memcpy랑 비슷한 성능이라 나름 좀 뿌듯하긴 하더라.


소스코드는 github에 msvc branch로 올려놨어. https://github.com/kukyakya/aligned_access/tree/msvc



코세야 이 정도 했으면 이젠 니 코드 가져오렴. 컴파일러가 지맘대로 memcpy로 슬쩍 바꿔놓은거 가지고 딸치는건지 진짜 제대로 도는건지 잘 확인해보고 가져오는 거 잊지 말고.