놀고 있는 비디오 메모리 활용

비디오 카드의 메모리의 용량은 적게는 32M에서 256M 정도 된다. 흔히 128M 정도의 카드가 많이 사용된다. 이 많은 비디오 카드의 메모리는 렌더링의 속도를 향상 시키기 위해서 3차원 그래픽 프로그램에서 사용된다. 하지만 3차원 그래픽 프로그램이 구동되지 않을 경우 대부분의 비디오 카드 메모리는 사용되지 않고 낭비된다. 예를들어 필자의 경우 해상도 1280×1024에서 32비트 색상을 사용하고 비디오 카드의 메모리는 128M이므로 128M에서 약 5M를 뺀 약 120M 정도의 비디오 메모리가 놀고 있는 셈이다.

그렇다면 이렇게 낭비되는 비디오 카드의 메모리를 3D 그래픽의 사용 목적이 아닌 일반 메모리처럼 사용할 수는 없을까? 게다가 비디오 카드의 메모리는 일반 메모리에 비해서 그 속도가 훨씬더 빠르다는 장점이 있지 않은가?

비디오 메모리를 사용하기 위해서는 당연히 비디오 메모리에 접근할 수 있어야 한다. 비디오 메모리에 접근하기 위한 API가 필요한데, 접근을 위한 특별한 API 라이브러리를 사용하는게 아니라 OpenGL과 DirectX의 API를 사용하면 되겠다. 여기서 필자에게 익숙한 OpenGL API를 사용하도록 하겠다.

비디오 메모리와 관련된 OpenGL API는 다음과 같다.

– glBindBuffer
– glBufferData
– glBufferSubData
– glDeleteBuffers
– glGenBuffers
– glMapBuffer
– glUnmapBuffer

위의 API는 ARB 군에 속해 있다가 OpenGL 1.5부터는 표준으로 안착되었다. 즉, OpenGL 1.5 이전에는 위의 함수명에다 접미사격으로 ARB를 붙여 사용해야 한다. 예를 들어서 glBindBuffer의 경우 glBindBufferARB 처럼 말이다. 물론 ARB의 경우는 Extension이므로 지원하는지의 여부를 먼저 확인해야 할 것이다. 확인을 위한 문자값은 GL_ARB_vertex_buffer_object이다.

각 함수의 내용에 대한 설명은 생략하고 사용하는 방법에 대해서만 살펴보겠다. 먼저 OpenGL을 초기화하고 현재 그래픽 카드가 지원하고 있는 OpenGL의 버전이 1.5 이상인지를 확인해야 한다. 여기서 한가지 문제점이 있는데, 그것은 바로 OpenGL의 초기화이다. OpenGL을 초기화하지 않으면 해당 API의 진입점을 찾지 못한다. 하지만 3D 기능을 사용하지도 않을 것인데, OpenGL을 초기화하해야한다는 것은 어쩌면 큰 부담이다. 특히 Console 프로그래밍과 같은 경우 렌더링 창에 대한 DC를 얻어와야 OpenGL을 초기화할 수 있는데, 이런 경우에 필자는 바탕화면의 DC를 사용하였다. 초기화를 위해 바탕화면의 DC를 사용하였을뿐, 실제로 무엇인가 렌더링하지는 않았기때문에 별 문제는 없으리라 본다.

어찌되었든 OpenGL을 초기화하고 OpenGL의 버전이 1.5 이상인 경우 위의 API의 진입점 포인트를 성공적으로 얻어왔다면 이제 사용하는 일만 남았다.

사용하는 방법은 정말 간단하다. 일반 메모리의 포인터를 얻어와 사용하는 방법과 유사하기 때문이다.

GLuint bufferID;

glGenBuffers(1, &bufferID);
glBindBuffer(GL_ARRAY_BUFFER, bufferID);
glBufferData(GL_ARRAY_BUFFER, sizeof(BYTE)*allocMemSize, NULL, GL_STATIC_DRAW);
BYTE *pBuffer = (BYTE *)glMapBuffer(GL_ARRAY_BUFFER, GL_READ_WRITE);

먼저 glGenBuffers를 사용하여 비디오 카드 메모리 버퍼의 ID를 생성하고 이 메모리 버퍼를 GL_ARRAY_BUFFER와 묶기 위해 glBindBuffer 함수를 사용한다. 그 후에 glBufferData를 사용하여 실제 비디오 메모리를 원하는 크기만큼 할당하는데 이 경우 가장 빠른 속도를 위해 GL_STATIC_DRAW를 사용하였다. 할당할 메모리의 크기는 자신이 사용하는 비디오 카드의 메모리의 크기를 잘 고려해서 지정하기 바란다. 여기까지 성공하였다면 할당 받은 비디오 카드의 메모리를 일반 메모리의 포인터처럼 사용하기 위해 메모리 주소값으로 Mapping 시키기 위해 glMapBuffer함수를 사용하여 포인터 주소를 얻어 온다. 바로 이 포인터 주소를 사용해서 일반 메모리와 똑같이 사용할 수 있는 것이다.

for(size_t i=0; i

위의 코드는 실제로 비디오 카드의 메모리를 마치 일반 포인터의 개념처럼 사용하는 예를 든 것이다.

이제는 이렇게 사용한 비디오 카드의 메모리를 해제시키는 방법은 다음 코드와 같다.

glUnmapBuffer(GL_ARRAY_BUFFER);
glDeleteBuffers(1, &bufferID);

필자가 시험삼아 10M의 메모리를 비디오 카드에 할당해 사용하는 방법과 일반 메모리에 new 연산자를 이용해 힙에 할당해서 사용하는 방법의 속도 차이를 비교해본 결과 약 3배정도의 속도 향상이 있음을 발견했다.

끝으로 이런 비디오 카드의 메모리의 속도의 장점을 잘활용한다면 빠른 속도를 요구하는 코드에 더욱 좋은 성능 향상을 꾀할 수 있을 것이다. 또한 비디오 메모리의 경우 일반 메모리에 비해 외부의 어플리케이션으로부터의 메모리 해킹이 어렵기 때문에 보안적인 면에서도 좋은 이점이 있을 것으로 생각된다.

201가지 소프트웨어 개발원칙

일반원칙
1. 품질이 제일이다.
2. 품질의 정의는 보는 사람에 따라 다르다,
3. 생산성과 품질은 불가분의 관계이다.
4. 고품질의 소프트웨어를 개발할 수 있다.
5. 사후에 품질을 만들어 넣으려 하지 말라.
6. 성능보다 신뢰성이 더 중요하다.
7. 시제품을 고객에게 빨리 보여준다.
8. 고객이나 사용자와 충분히 협의한다.
9. 개발자와 고객에게 적합한 보상기준을 마련한다.
10. 처음 시도하는 것은 폐기할 작정으로 개발한다.
11. 적절한 유형의 시제품을 개발한다.
12. 적절한 기능을 시제품화 한다.
13. 일회용 시제품은 빨리 개발한다.
14. 시스템을 점증적으로 개발한다.
15. 보면 볼수록 더 많은 것을 원한다.
16. 개발중의 변경은 피할 수 없다.
17. 가능하면 개발하기 보다는 구매한다.
18. 사용자 매뉴얼이 간단하게 되도록 소프트웨어를 개발한다.
19. 아무리 복잡한 문제라도 해결책은 있다.
20. 가정한 것이 있으면 이를 기록한다.
21. 다른 단계에는 다른 언어를 사용한다.
22. 도구를 사용하기 전에 기법을 배운다.
23. 도구는 현실적으로 사용한다.
24. 소프트웨어 도구는 우수한 개발자에게만 제공한다.
25. CASE도구는 고가이다.
26. “Know-How”만큼 “Know-When”도 중요하다.
27. 목적을 달성하면 중단한다.
28. 정형적 방법을 알아야 한다.
29. 조직의 평판을 중시한다.
30. 대세를 따를 때는 주의해야 한다.
31. 기술을 무시하면 안된다.
32. 문서 표준을 사용한다.
33. 모든 문서에는 용어정의를 한다.
34. 모든 문서에는 색인을 부여한다.
35. 같은 개념에는 같은 명칭을 사용한다.
36. 연구결과의 기술이전은 즉시 되지 않는다.
37. 책임을 질 줄 알아야 한다.

요구공학 원칙
38. 요구사항이 불명확할수록 비용예측은 어렵다.
39. 요구사항을 기록하기 전에 문제를 확실하게 결정한다.
40. 지금 요구사항을 결정한다.
41. 요구명세상의 오류는 즉시 수정해야 한다.
42. 시제품으로 사용자 인터페이스 선정의 위험을 줄인다.
43. 요구사항 항목의 선정근거를 기록한다.
44. 최소 요구사항을 식별한다.
45. 요구사항을 검토한다.
46. 요구분석단계에서 설계하지 않는다.
47. 올바른 기법을 사용한다.
48. 여러 관점으로 요구사항을 분석한다.
49. 요구사항을 현명하게 조직화한다.
50. 요구사항의 우선순위를 정한다.
51. 간결하게 기록한다.
52. 모든 요구사항에 유일한 식별번호를 부여한다.
53. 요구사항의 모호성을 줄인다.
54. 자연어는 정형모델로 보완만 하고 대체하지는 말라.
55. 먼저 자연어로 기록하고 정형모델을 작성하라.
56. 요구명세서는 읽기 쉬워야 한다.
57. 신뢰성에 대하여 구체적으로 명시한다.
58. “수용 불가능한” 환경조건을 명시한다.
59. 미결정항목은 각주와 함께 작성한다.
60. 요구명세서를 데이터베이스에 저장한다.

설계 원칙
61. 요구사항에서 설계로의 전환은 어렵다.
62. 설계산출물에서 요구사항을 추적한다.
63. 대안을 평가한다.
64. 문서가 없는 설계는 설계가 아니다.
65. 캡슐화 한다.
66. 가능하면 재사용한다.
67. 단순하게 개발한다.
68. 특수한 경우를 많이 만들지 않는다.
69. 지적인 거리를 최소화 한다.
70. 설계를 지적 통제하에 둔다.
71. 개념적 무결성을 유지한다.
72. 개념적 오류는 문법적 오류보다 심각하다.
73. 결합도는 낮추고 응집도는 높인다.
74. 변경이 쉽게 설계한다.
75. 유지보수를 고려하여 설계한다.
76. 오류수정이 쉽게 설계한다.
77. 일반성을 띄게 소프트웨어를 개발한다.
78. 유연성 있게 소프트웨어를 개발한다.
79. 효율적인 알고리즘을 사용한다.
80. 사용자가 필요로 하는 모든 정보는 모듈명세서에 있다.
81. 설계는 다차원적이다.
82. 뛰어난 설계는 뛰어난 설계자가 한다.
83. 어플리케이션에 대해서 숙지한다.
84. 큰 투자 없이도 재사용할 수 있다.
85. 무효한 값을 입력하면 적절한 오류 메세지를 출력하도록 한다.
86. 소프트웨어 신뢰성은 중복성을 통해 얻을 수 있다.

코딩원칙
87. 트릭을 사용하지 않는다.
88. 광역변수를 사용하지 않는다.
89. 하향식으로 읽을 수 있도록 작성한다.
90. 부작용을 제거한다.
91. 의미 있는 명칭을 사용한다.
92. 사람을 위한 프로그램을 작성한다.
93. 최적의 자료구조를 사용한다.
94. 빨리 하기 보다는 올바르게 한다.
95. 코드를 완성하기 전에 주석을 작성한다.
96. 코딩을 시작하기 전에 문서화한다.
97. 모든 구성요소를 책상 위에서 실행시켜 본다.
98. 코드 검사를 실시한다.
99. 비구조적 언어도 사용할 수 있다.
100. 구조화된 코드가 반드시 좋은 코드는 아니다.
101. 너무 깊이 중첩 시키지 않는다.
102. 적절한 언어를 사용한다.
103. 프로그래밍 언어를 핑계 삼아서는 안된다.
104. 언어에 대한 지식은 중요하지 않다.
105. 프로그램의 체계를 정비한다.
106. 코딩을 너무 빨리 시작하지 말아라.

시험원칙
107. 시험에서 요구사항을 추적한다.
108. 시험하기 훨씬 이전에 시험을 계획한다.
109. 자신이 개발한 소프트웨어를 자신이 시험하지 않는다.
110. 자신이 개발한 소프트웨어의 시험계획은 남이 세운다.
111. 시험은 결함을 드러나게 할 뿐이다.
112. 오류의 많고 적음과 소프트웨어의 가치는 무관하다.
113. 오류를 찾아야 성공적인 시험이다.
114. 15% 모듈에서 50%의 오류가 발견된다.
115. 블랙박스시험과 화이트박스시험을 실시한다.
116. 시험사례에는 예상결과를 포함시킨다.
117. 무효한 값으로 시험한다.
118. 항상 스트레스 시험을 한다.
119. 빅뱅설을 적용하면 안된다.
120. McCabe의 복잡도 척도를 사용한다.
121. 효과적인 시험종료 척도를 사용한다.
122. 시험 적용범위를 효과적으로 활용한다.
123. 단위시험이 끝나기 전에 통합하지 않는다.
124. 소프트웨어에 특정한 시험용 코드를 내장시킨다.
125. 오류의 원인을 분석한다.
126. 오류를 개인적인 차원으로 생각하지 않는다.

관리원칙
127. 뛰어난 관리는 뛰어난 기술보다 중요하다.
128. 적절한 해결책을 이용한다.
129. 읽은 것을 모두 믿지 않는다.
130. 고객의 우선순위를 알아야 한다.
131. 사람이 성공의 열쇠이다.
132. 많은 사람보다는 소수정예요원이 더 낫다.
133. 부하 직원의 말을 경청한다.
134. 부하 직원을 신뢰해야 한다.
135. 항상 기대치를 높이 가진다.
136. 능숙한 의사소통 기술은 필수적이다.
137. 진심으로 부하직원을 위해준다.
138. 사람은 의외의 것으로 동기부여 받는다.
139. 사무실 분위기를 조용히 유지한다.
140. 인력과 시간은 대체할 수 없다.
141. 소프트웨어 개발자의 능력차이는 크다.
142. 원하는 목표로 최적화 할 수 있다.
143. 자료수집을 강요하면 안된다.
144. 코드 1줄 당 비용은 무시한다.
145. 완벽한 생산성 측정방법은 없다.
146. 비용산정 모델을 조정한다.
147. 일정은 현실적으로 계획한다.
148. 불가능한 것은 피한다.
149. 측정하기 전에 무엇을 측정할 지 알아야 한다.
150. 생산성 자료를 수집한다.
151. 팀의 생산성을 잊지 않는다.
152. 인월 당 행수(LOC/PM)은 언어와 관계없다.
153. 일정을 믿는다.
154. 정확하게 산정한 비용견적이라도 완전히 맞지는 않는다.
155. 일정을 정기적으로 재조정한다.
156. 약간 적은 견적을 항상 나쁘다고 할 수는 없다.
157. 자원을 적절히 할당한다.
158. 프로젝트를 치밀하게 계획한다.
159. 계획을 최신 버전으로 유지한다.
160. 잦은 계획변경의 파급효과에 주의한다.
161. 최상위 10개의 위험항목을 알아야 한다.
162. 직면한 위험을 이해한다.
163. 적절한 프로세스 모델을 사용한다.
164. 방법론이 당신을 구해주지는 못한다.
165. 기적적인 생산성 향상 비법은 없다.
166. 진척도의 의미를 정확히 알아야 한다.
167. 계획과의 차이만 관리한다.
168. 하드웨어에 과중한 부하를 주지 않는다.
169. 하드웨어의 발전에는 낙천적으로 대응한다.
170. 소프트웨어의 발전에는 비관적으로 대응한다.
171. 예상치 못한 사고로 인해 대혼란이 자주 초래된다.
172. 프로젝트의 사후 검토회를 실시한다.

제품보증 원칙
173. 제품보증 수준은 프로젝트에 맞게 조정한다.
174. 형상관리 절차를 조기에 확립한다.
175. 소프트웨어 프로세스에 SCM을 적용한다.
176. SCM은 프로젝트 관리에 독립적으로 조직화한다.
177. 개발과 제품보증업무 사이를 순환보직화 한다.
178. 모든 중간산출물에 명칭과 버전 번호를 부여한다.
179. 기준선을 통제한다.
180. 모든 것을 보존한다.
181. 모든 변경을 계속 추적한다.
182. 변경관리를 해야 한다.
183. 변경요청에 우선순위를 부여하고 일정계획을 세운다.
184. 대규모 개발에는 검증과 확인(V&V)을 적용한다.

진화원칙
185. 소프트웨어는 계속 변화한다.
186. 소프트웨어의 엔트로피는 증가한다.
187. 고장나지 않았으면 고치지 않는다.
188. 증상이 아닌 근본적인 문제를 수정한다.
189. 요구사항을 먼저 변경한다.
190. 릴리즈 전의 오류는 릴리즈 후의 오류의 원인이 된다.
191. 프로그램은 오래되면 될수록 유지보수하기 어려워진다.
192. 언어는 유지보수성에 영향을 미친다.
193. 때로는 처음부터 수정하는 방법이 좋다.
194. 최악의 구성요소는 처음부터 다시 개발한다.
195. 유지보수는 개발보다 많은 오류를 발생시킨다.
196. 변경한 후에는 반드시 회기 시험을 실시한다.
197. 변경사항이 간단하다고 방심하면 잘못 변경하게 된다.
198. 비구조적인 코드는 구조화해도 개선되지 않는다.
199. 최적화하기 전에 프로파일러를 사용한다.
200. 시스템에 친밀감을 갖는다.
201. 시스템은 환경변화에 따라 계속 변화한다.

출처 : ‘201가지 소프트웨어 개발원칙’ 목차

이쁜 마나..

가만.. 근데 이것들 삥아리 같은데…. 어린것들이 이러다가 일 내징… ㅡ,.ㅡ;

올해의 가운데서, 아버지에게..

모처럼 시골집에 들렸습니다. 아버지를 보며… 이제는 평안하시라고 기원해 드립니다. 난 아직도 기억합니다. 당신의 그 힘들었던 시절을… 어린 자식였던, 나 조차도 아버지의 그 육신과 심신의 힘겨움마저 느낄 정도 였지요. 하지만 아버지께서는 그 힘듬을 겨우…. 버텨내시고 당신의 가족에 대한 하나의 사명을 다 하셨죠.. 아버지 이제는 평안하셔요… 제가 모르는 고통스런 역경이 훨씬 더 많았을테지요.. 이제는 진실로 평안한 모습으로 우리 곁에 계시는 것이 당신의 사명이십니다.. 텔레비젼을 보시며 험한 욕을 한바탕 하고 분을 삭히지 못하시지요. 수년.. 아니 수개월 전까지만 해도 그런 아버지의 모습을 이해하지 못했지요.. 하지만 이제는 조금 이해할 수 있을듯합니다. 아니… 이해해 드릴 수 있을 것 같습니다. 답답하고 모진 이 삶의 푸념을 하소연할 곳이 마땅치 않았던 당신. 마침내는 텔레비전을 하소연할 곳으로 삼으셨던 것이였죠… 죄송스럽습니다. 그런 당신을 좀더 일찍 이해해 드리지 못하고 오히려 당신에게 화를 냈던 이 못난 자식을… 소주를 좋아하시는 아버지… 당신과 마자앉아 소주잔을 즐거이 주고 받을 수 있도록… 소주 주량을 늘려야겠습니다…
[출처] www.DCinside.co.kr