๋ฉ๋ชจ๋ฆฌ ๋์(Memory leak)๋ ?
retain cycle๋ก ์ธํด ๋ฉ๋ชจ๋ฆฌ์์ ๊ฐ์ฒด๋ฅผ ํ ๋น ํด์ ํ ์ ์๋ ๊ฒฝ์ฐ์ ๋ฐ์ํ๋ค. Swift๋ ARC๋ฅผ ํตํด ๋ฉ๋ชจ๋ฆฌ ๊ด๋ฆฌ๋ฅผ ํ๋๋ฐ, ๋ ๊ฐ์ฒด ์ด์์ด ์๋ก์ ๋ํด ๊ฐํ ์ฐธ์กฐ๋ฅผ ํ๋ ๊ฒฝ์ฐ์ retain cycle์ด ๋ฐ์ํ๋ค. ๊ฒฐ๊ณผ์ ์ผ๋ก ์ฐธ์กฐ ์นด์ดํ
์ด 0์ด ๋์ง ์์ deinit์ด ํธ์ถ๋์ง ์๋๋ค.
์ด๋ฅผ ๋ฐฉ์งํ๊ธฐ ์ํด์ ๊ฐ์ฒด๊ฐ์ ์ํธ์ฐธ์กฐํ๋ ๊ฒฝ์ฐ weak, unowned ํค์๋๋ฅผ ํตํด ์ฝํ์ฐธ์กฐ๋ฅผ ์ฌ์ฉํด์ผํ๋ค.
(์์ธํ ๋ด์ฉ์ ARC์ ๋ํด ์์๋ณด๋ฉด ๋๋ค.)
class A{
var b: B?
}
class B{
var a: A?
}
func makeMemoryLeaks(){
let a = A()
let b = B()
a.b = b
b.a = a
}
๊ฐ๋จํ ์๋ฅผ ๋ค๋ฉด , a๋ ํด๋์ค B์ ์ธ์คํด์ค์ธ b๋ฅผ ์ฐธ์กฐํ๋ค. ๊ทธ๋ฆฌ๊ณ ํด๋์ค B์ ์ธ์คํด์ค b ๋ ํด๋์ค A์ ์ธ์คํด์ค a ๋ฅผ ์ฐธ์กฐํ๊ณ ์๋ค. ๋ฐ๋ผ์ a, b๋ ๊ฒฐ๊ตญ ๋๊น์ง ๋ ํผ๋ฐ์ค ์นด์ดํธ๋ฅผ 1๋ก ์ ์งํ๋ฉฐ ํ ๋น ํด์ ๋์ง ๋ชปํ์ฑ ๋ฉ๋ชจ๋ฆฌ ๋์๋ฅผ ๋ฐ์์ํจ๋ค.
๊ทธ๋ ๋ค๋ฉด ๋ฉ๋ชจ๋ฆฌ ๋์๋ฅผ ์ด๋ป๊ฒ ๋ฐ๊ฒฌํ ์ ์์๊น?
์ฌ๋ฌ๊ฐ์ง ๋ฐฉ๋ฒ์ด ์๊ฒ ์ง๋ง, ๋ ๊ฐ์ง ๋ฐฉ๋ฒ์ ์ฐพ์๋ณด์๋ค.
- Xcode - Memory graph debugger
- Instrument - Leaks
1. Xcode - Memory graph debugger
์ค์
์คํํ๊ธฐ ์ ์ Edit Scheme๋ก ๋ค์ด๊ฐ์ Diagnostics ์ค์ ์ ์ ์ฌ์ง์ฒ๋ผ ๋ฐ๊พธ์ด์ค๋ค.
- Live Allocation Only : All Allocations ๋ณด๋ค ์ค๋ฒํค๋๊ฐ ์ ๋ค. ๋ฆฌํ
์ธ ์ฌ์ดํด์ด๋ ๋ฉ๋ชจ๋ฆฌ ๋์๋ฅผ ์๋ณํ ๋ ํ์ํ ํญ๋ชฉ.
์คํ
Xcode ์ฝ์์ฐฝ ์๋ถ๋ถ์ ์๋ ๋ฒํผ์ ํด๋ฆญํ๋ฉด ์คํํ ์ ์๋ค.
๋ฒํผ์ ๋๋ฅด๊ฒ ๋๋ฉด ์ฑ ์คํ์ ์ค์งํ๊ณ ํ์ฌ ์ํ์ ํ์ ๋ํด ์ค๋
์ท์ ์ฐ๋๋ค. ๊ทธ๋ฆฌ๊ณ ๋จ์์๋ ๊ฐ์ฒด๋ค๊ณผ ๋ฉ๋ชจ๋ฆฌ์ ์ ์ง๋๊ณ ์๋ ์ฐธ์กฐ ์ฒด์ธ์ด ํ์๋๋ค.
์ข์ธก์ ํ์ ์๋ ๊ฐ์ฒด ๋ฆฌ์คํธ๋ค์ด ๋ํ๋๋ค. ์ธ์คํด์ค ์ด๋ฆ, ์ธ์คํฐ์ค์ ๊ฐ์, ๊ทธ๋ฆฌ๊ณ ์ธ์คํด์ค์ ์ฃผ์๊ฐ ๋ฑ์ด ํ์๋๋ค.
๊ทธ๋ฆฌ๊ณ ๋ณด๋ผ์ ๊ฒฝ๊ณ ํ์๋ ๋ฉ๋ชจ๋ฆฌ ๋์์ ๋ํ ๊ฒฝ๊ณ ์ด๋ค. ์๊น ํด๋์ค A, B๋ฅผ ์๋ก ์ํธ์ฐธ์กฐ ํ๊ฒํ์๋๋ Xcode๊ฐ ๊ฐ์งํ๊ณ ์๋ ค์ฃผ๋ ๋ชจ์ต์ด๋ค.
์ค์ํ ์ ์ ๋ฉ๋ชจ๋ฆฌ ๋์๋ Xcode๊ฐ ์๋์ผ๋ก ์ฐพ์์ฃผ๋ ๊ฒฝ์ฐ ๋ณด๋ค ๊ฐ๋ฐ์๊ฐ ์ง์ ์ฐพ์์ผ ํ๋ ๊ฒฝ์ฐ๊ฐ ๋ ๋ง๋ค. ์ค์ ๋ก ๋ช๊ฐ์ Retain cycle์ ๋ง๋ค์ด ํ
์คํธ ํด ๋ณด์๋๋ฐ, ์๋ ๊ฐ์ง๊ฐ ์๋๋ ๊ฒฝ์ฐ๊ฐ ๋ ๋ง์๋ค. ํด๋น ์ฝ๋๋ ๊ฒ์๊ธ ํ๋จ์ git๋ ํฌ์ ์๋ค.
A (3)
0x60000210c5a0
0x6000010c05a0
0x6000020c13a0
๊ฐ์ฒด (์ธ์คํด์ค์ ๊ฐ์)
์ธ์คํด์ค์ ์ฃผ์
Object references
๊ฐ์ฒด๋ฅผ ํด๋ฆญํ๋ฉด ์์ ๊ฐ์ ๊ฐ์ฒด ๊ทธ๋ํ๋ค์ด ๊ทธ๋ฆผ์ผ๋ก ๋ํ๋๋ค.
๊ตต์์ → ๊ฐํ ์ฐธ์กฐ๋ฅผ ์๋ฏธํ๋ค.
์ฐํ์ → ์ ์ ์๋ ์ฐธ์กฐ๋ฅผ ์๋ฏธํ๋ค. (๊ฐํ ์ฐธ์กฐ์ผ ์๋ ์๊ณ , ์ฝํ ์ฐธ์กฐ์ผ ์ ๋ ์๋ค.)
๊ฐ๋จํ๊ฒ ๋ฉ๋ชจ๋ฆฌ ๊ทธ๋ํ ๋๋ฒ๊ฑฐ์ ๊ธฐ๋ฅ์ ๋ํด ์์๋ดค๋ค.
๊ทธ๋ ๋ค๋ฉด ๋์๋ฅผ ํ์ธํ๋ ค๋ฉด ์ด๋ป๊ฒ ํ ๊น?
ํ
์คํธํ ๊ธฐ๋ฅ์ ๋ํด ์คํํ๊ณ , ์ด๋ฅผ ์ฌ๋ฌ๋ฒ ๋ฐ๋ณตํ๋ค. ๊ทธ๋ฆฌ๊ณ ์ฑ์ ์ค๋
์ท์ ํ์ธํ๋ค.
- ๋ฐ๋ณต์ ์ผ๋ก ๊ธฐ๋ฅ์ ํ
์คํธํ์๋ ๋ฉ๋ชจ๋ฆฌ ์ฌ์ฉ๋์ด ๋์ด๋ฌ๋ค๋ฉด ๋์๋ฅผ ์์ฌํ ์ ์๋ค.
- ์ธ์คํด์ค ๊ฐ์๊ฐ ๋ง์๋ ๋ฉ๋ชจ๋ฆฌ ๋์ ์งํ์ผ ์ ์๋ค.
- ์ผ์ชฝ ํจ๋ ๋ฆฌ์คํธ์ ํ์ฌ ์ฑ ์ํ์์ ์์ผ๋ฉด ์๋๋ ๊ฐ์ฒด/ํด๋์ค/๋ทฐ ๋ฑ์ด ํ์๋๊ณ ์๋์ง ํ์ธํ๋ค.
Instruments - Leaks
Instrument๋ ์ค๋
์ท์ ์ฐ๋๊ฒ ์๋๋ผ ๋ค์ด๋๋ฏนํ๊ฒ ๋ฉ๋ชจ๋ฆฌ๋ฅผ ํ๋กํ์ผ๋ง ํ ์ ์๋ค. (์คํํด๋ ์ฑ์ด ์ผ์์ ์ง ๋์ง ์์ผ๋ฉฐ, ์ฑ์์ ๊ธฐ๋ฅ์ ์คํ์ํค๋ฉด ๋์ ์ผ๋ก ์ธ์คํด์ค๋ค๊ณผ ๋ฉ๋ชจ๋ฆฌ๋ฅผ ์ถ์ ํ๋ค)
instrument์์ Leaks๋ฅผ ์คํ์ํจ๋ค.
๊ทธ๋ฆฌ๊ณ ์๋จ์ ๋๋ฒ๊น
ํ Target(์ฑ)์ ์ ํํ ์ ์๋ค.
๊ทธ๋ฆฌ๊ณ ๋นจ๊ฐ์ ๋
นํ๋ฒํผ? ์ ๋ฎ์ ๋ฒํผ์ ํด๋ฆญํ๋ฉด Leaks์ด ๋์ํ๋ค.
๊ฐ์ง๋ ์ธ์คํด์ค์ ๋ํ ๋ชฉ๋ก๊ณผ ARC์ ๋ ํผ๋ฐ์ค ์นด์ดํธ๊น์ง ํ์๋๋ค.
ํ๋จ ํํฐ์์ ํ์ฌ ์คํ์ค์ธ ์ฑ ์ด๋ฆ์ ๊ฒ์ํ๋ฉด ๊ด๋ จ์๋ ์ธ์คํด์ค๋ค์ ๋ํด์๋ง ํธํ๊ฒ ๋ณผ ์ ์๋ค.
Memory Leak Test
https://github.com/Youjunyong/MemoryLeaks.git
์ฐธ๊ณ ์๋ฃ
https://www.youtube.com/watch?v=b2AgibUg47k
https://doordash.engineering/2019/05/22/ios-memory-leaks-and-retain-cycle-detection-using-xcodes-memory-graph-debugger/