Leaked source code of windows server 2003
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

528 lines
11 KiB

  1. //+-------------------------------------------------------------------------
  2. //
  3. // Microsoft Windows
  4. //
  5. // Copyright (C) Microsoft Corporation, 1998 - 1999
  6. //
  7. // File: dpmsgobj.cpp
  8. //
  9. //--------------------------------------------------------------------------
  10. #include "stdafx.h"
  11. #include "Direct.h"
  12. #include "dms.h"
  13. #include "dpMsgObj.h"
  14. #include "dplconnectionobj.h"
  15. #include "dpsessdataobj.h"
  16. extern HRESULT BSTRtoGUID(LPGUID,BSTR);
  17. extern BSTR GUIDtoBSTR(LPGUID);
  18. HRESULT C_dxj_DirectPlayMessageObject::create(DWORD from,DWORD size,void **data,I_dxj_DirectPlayMessage **ret)
  19. {
  20. HRESULT hr;
  21. if (!ret) return E_INVALIDARG;
  22. C_dxj_DirectPlayMessageObject *c=NULL;
  23. c=new CComObject<C_dxj_DirectPlayMessageObject>;
  24. if( c == NULL ) return E_OUTOFMEMORY;
  25. c->init(from);
  26. if (size!=0) {
  27. hr=c->AllocData(size);
  28. if FAILED(hr){
  29. delete c;
  30. return E_OUTOFMEMORY;
  31. }
  32. *data=c->m_pData;
  33. }
  34. hr=c->QueryInterface(IID_I_dxj_DirectPlayMessage, (void**)ret);
  35. return hr;
  36. }
  37. HRESULT C_dxj_DirectPlayMessageObject::init(DWORD f){
  38. if (!f)
  39. m_fSystem=TRUE;
  40. else
  41. m_fSystem=FALSE;
  42. return S_OK;
  43. }
  44. C_dxj_DirectPlayMessageObject::C_dxj_DirectPlayMessageObject()
  45. {
  46. m_dwSize=0;
  47. m_pData=NULL;
  48. m_fSystem=FALSE;
  49. m_nWriteIndex=0;
  50. m_nReadIndex=0;
  51. }
  52. C_dxj_DirectPlayMessageObject::~C_dxj_DirectPlayMessageObject()
  53. {
  54. clear();
  55. }
  56. HRESULT C_dxj_DirectPlayMessageObject::writeString(BSTR string)
  57. {
  58. if (!string) return E_INVALIDARG;
  59. //read the length of the string
  60. DWORD l= (((DWORD*)string)[-1]);
  61. DWORD growSize=l*sizeof(WCHAR)+sizeof(DWORD);
  62. if (m_nWriteIndex+growSize>=m_dwSize) {
  63. if FAILED(GrowBuffer(growSize)) return E_OUTOFMEMORY;
  64. }
  65. //save a DWORD with the length of the string
  66. *((DWORD*)(m_pData+m_nWriteIndex)) =l;
  67. //increment our write pointer past the DWORD
  68. m_nWriteIndex=m_nWriteIndex+sizeof(DWORD);
  69. //save the string to our buffer
  70. wcscpy((WCHAR*) &(m_pData[m_nWriteIndex]),string);
  71. //increment the write pointer passed the data we wrote
  72. m_nWriteIndex=m_nWriteIndex+l*sizeof(WCHAR);
  73. return S_OK;
  74. }
  75. HRESULT C_dxj_DirectPlayMessageObject::readString(BSTR *string)
  76. {
  77. DWORD l;
  78. WCHAR *pstr=NULL;
  79. //make sure m_pData is set
  80. if (!m_pData) return E_OUTOFMEMORY;
  81. //make sure we havent gone past
  82. if (m_nReadIndex>m_dwSize) return E_FAIL;
  83. if (m_dwSize< m_nReadIndex+sizeof(DWORD)) return E_FAIL;
  84. if (m_fSystem){
  85. pstr=*((WCHAR**)(m_pData+m_nReadIndex));
  86. m_nReadIndex=m_nReadIndex+sizeof(DWORD); //move on to the next arg if fail on a system message
  87. __try {
  88. *string=SysAllocString(pstr);
  89. }
  90. __except(1,1){
  91. return E_FAIL;
  92. }
  93. }
  94. else {
  95. //extract the length of the string
  96. l= *((DWORD*)(m_pData+m_nReadIndex));
  97. m_nReadIndex=m_nReadIndex+sizeof(DWORD);
  98. if (m_dwSize< m_nReadIndex+l*sizeof(WCHAR)) return E_FAIL;
  99. *string=SysAllocString((WCHAR*)&(m_pData[m_nReadIndex]));
  100. m_nReadIndex=m_nReadIndex+l*sizeof(WCHAR);
  101. }
  102. return S_OK;
  103. }
  104. HRESULT C_dxj_DirectPlayMessageObject::writeLong(long val)
  105. {
  106. DWORD growSize=sizeof(long);
  107. if (m_nWriteIndex+growSize>=m_dwSize) {
  108. if FAILED(GrowBuffer(growSize)) return E_OUTOFMEMORY;
  109. }
  110. *((long*) &(m_pData[m_nWriteIndex]))=val;
  111. m_nWriteIndex=m_nWriteIndex+sizeof(long);
  112. return S_OK;
  113. }
  114. HRESULT C_dxj_DirectPlayMessageObject::readLong(long *val)
  115. {
  116. if (!m_pData) return E_FAIL;
  117. if (m_nReadIndex>m_dwSize) return E_FAIL;
  118. *val= *((long*)(m_pData+m_nReadIndex));
  119. m_nReadIndex=m_nReadIndex+sizeof(long);
  120. return S_OK;
  121. }
  122. HRESULT C_dxj_DirectPlayMessageObject::writeShort(short val)
  123. {
  124. DWORD growSize=sizeof(short);
  125. if (m_nWriteIndex+growSize>=m_dwSize) {
  126. if FAILED(GrowBuffer(growSize)) return E_OUTOFMEMORY;
  127. }
  128. *((short*) (&m_pData[m_nWriteIndex]))=val;
  129. m_nWriteIndex=m_nWriteIndex+sizeof(short);
  130. return S_OK;
  131. }
  132. HRESULT C_dxj_DirectPlayMessageObject::readShort(short *val)
  133. {
  134. if (!m_pData) return E_OUTOFMEMORY;
  135. if (m_nReadIndex>m_dwSize) return E_FAIL;
  136. *val= *((short*)(m_pData+m_nReadIndex)) ;
  137. m_nReadIndex=m_nReadIndex+sizeof(short);
  138. return S_OK;
  139. }
  140. HRESULT C_dxj_DirectPlayMessageObject::writeSingle(float val)
  141. {
  142. DWORD growSize=sizeof(float);
  143. if (m_nWriteIndex+growSize>=m_dwSize) {
  144. if FAILED(GrowBuffer(growSize)) return E_OUTOFMEMORY;
  145. }
  146. *((float*)&(m_pData[m_nWriteIndex]))=val;
  147. m_nWriteIndex=m_nWriteIndex+sizeof(float);
  148. return S_OK;
  149. }
  150. HRESULT C_dxj_DirectPlayMessageObject::readSingle(float *val)
  151. {
  152. if (!m_pData) return E_OUTOFMEMORY;
  153. if (m_nReadIndex>m_dwSize) return E_FAIL;
  154. *val= *((float*)(m_pData+m_nReadIndex)) ;
  155. m_nReadIndex=m_nReadIndex+sizeof(float);
  156. return S_OK;
  157. }
  158. HRESULT C_dxj_DirectPlayMessageObject::writeDouble(double val)
  159. {
  160. DWORD growSize=sizeof(double);
  161. if (m_nWriteIndex+growSize>=m_dwSize) {
  162. if FAILED(GrowBuffer(growSize)) return E_OUTOFMEMORY;
  163. }
  164. *((double*)(&m_pData[m_nWriteIndex]))=val;
  165. m_nWriteIndex=m_nWriteIndex+sizeof(double);
  166. return S_OK;
  167. }
  168. HRESULT C_dxj_DirectPlayMessageObject::readDouble(double *val)
  169. {
  170. if (!m_pData) return E_FAIL;
  171. if (m_nReadIndex>m_dwSize) return E_FAIL;
  172. *val= *((double*)(m_pData+m_nReadIndex));
  173. m_nReadIndex=m_nReadIndex+sizeof(double);
  174. return S_OK;
  175. }
  176. HRESULT C_dxj_DirectPlayMessageObject::writeByte(Byte val)
  177. {
  178. DWORD growSize=sizeof(BYTE);
  179. if (m_nWriteIndex+growSize>=m_dwSize) {
  180. if FAILED(GrowBuffer(growSize)) return E_OUTOFMEMORY;
  181. }
  182. *((BYTE*)&(m_pData[m_nWriteIndex]))=val;
  183. m_nWriteIndex=m_nWriteIndex+sizeof(BYTE);
  184. return S_OK;
  185. }
  186. HRESULT C_dxj_DirectPlayMessageObject::readByte(Byte *val)
  187. {
  188. if (!m_pData) return E_FAIL;
  189. if (m_nReadIndex>m_dwSize) return E_FAIL;
  190. *val= *((BYTE*)(m_pData+m_nReadIndex)) ;
  191. m_nReadIndex=m_nReadIndex+sizeof(BYTE);
  192. return S_OK;
  193. }
  194. HRESULT C_dxj_DirectPlayMessageObject::writeGuid(BSTR string)
  195. {
  196. HRESULT hr;
  197. DWORD growSize=sizeof(GUID);
  198. if (m_nWriteIndex+growSize>=m_dwSize) {
  199. if FAILED(GrowBuffer(growSize)) return E_OUTOFMEMORY;
  200. }
  201. hr=BSTRtoGUID((LPGUID)&(m_pData[m_nWriteIndex]),string);
  202. if FAILED(hr) return hr;
  203. //increment our write pointer past the DWORD
  204. m_nWriteIndex=m_nWriteIndex+sizeof(GUID);
  205. return S_OK;
  206. }
  207. HRESULT C_dxj_DirectPlayMessageObject::readGuid(BSTR *string)
  208. {
  209. //make sure m_pData is set
  210. if (!m_pData) return E_FAIL;
  211. //make sure we havent gone past
  212. if (m_nReadIndex>m_dwSize) return E_FAIL;
  213. if (m_dwSize < m_nReadIndex+sizeof(GUID)) return E_FAIL;
  214. *string=GUIDtoBSTR( (LPGUID) &(m_pData[m_nReadIndex]) );
  215. return S_OK;
  216. }
  217. HRESULT C_dxj_DirectPlayMessageObject::moveToTop()
  218. {
  219. m_nReadIndex=0;
  220. return S_OK;
  221. }
  222. HRESULT C_dxj_DirectPlayMessageObject::getMessageSize(long *ret)
  223. {
  224. *ret=m_dwSize;
  225. return S_OK;
  226. }
  227. HRESULT C_dxj_DirectPlayMessageObject::getMessageData(void *ret)
  228. {
  229. __try{
  230. memcpy(ret,m_pData,m_dwSize);
  231. }
  232. __except(1,1){
  233. return E_FAIL;
  234. }
  235. return S_OK;
  236. }
  237. HRESULT C_dxj_DirectPlayMessageObject::setMessageData(void *data, long size)
  238. {
  239. clear();
  240. m_dwSize=(DWORD)size;
  241. m_pData=(char*)malloc(size);
  242. if (!m_pData) return E_OUTOFMEMORY;
  243. __try{
  244. memcpy(m_pData,data,m_dwSize);
  245. }
  246. __except(1,1){
  247. return E_INVALIDARG;
  248. }
  249. return S_OK;
  250. }
  251. HRESULT C_dxj_DirectPlayMessageObject::clear()
  252. {
  253. if (m_pData) free(m_pData);
  254. m_dwSize=0;
  255. m_pData=NULL;
  256. m_fSystem=FALSE;
  257. m_nWriteIndex=0;
  258. m_nReadIndex=0;
  259. return S_OK;
  260. }
  261. HRESULT C_dxj_DirectPlayMessageObject::getPointer(long *ret)
  262. {
  263. *ret=(long)PtrToLong(m_pData); //bugbug SUNDOWN
  264. return S_OK;
  265. }
  266. HRESULT C_dxj_DirectPlayMessageObject::AllocData(long size)
  267. {
  268. clear();
  269. m_pData=(char*)malloc(size);
  270. if (!m_pData) return E_OUTOFMEMORY;
  271. ZeroMemory(m_pData,size);
  272. m_dwSize=size;
  273. return S_OK;
  274. }
  275. HRESULT C_dxj_DirectPlayMessageObject::GrowBuffer(DWORD size){
  276. if (m_pData)
  277. {
  278. void* tmp = realloc(m_pData,m_dwSize+size);
  279. if (tmp)
  280. m_pData=(char*)tmp;
  281. else
  282. return E_FAIL;
  283. if (!m_pData) return E_FAIL;
  284. }
  285. else
  286. {
  287. m_pData=(char*)malloc(m_dwSize+size);
  288. if (!m_pData) return E_FAIL;
  289. }
  290. m_dwSize=m_dwSize+size;
  291. return S_OK;
  292. }
  293. HRESULT C_dxj_DirectPlayMessageObject::readSysMsgData(BSTR *ret)
  294. {
  295. if (!m_pData) return E_FAIL;
  296. WCHAR *pstr;
  297. DWORD size;
  298. DWORD type;
  299. //valid on DPSYS_CREATEPLAYERORGROUP
  300. //valid on DPSYS_DESTROYPLAYERORGROUP
  301. //valid on DPSYS_SETPLAYERORGROUPDATA
  302. //make sure we have enough space to check the type
  303. if (m_dwSize<4) return E_FAIL;
  304. type= *((DWORD*)(m_pData));
  305. if (!((type==DPSYS_CREATEPLAYERORGROUP)||(type==DPSYS_DESTROYPLAYERORGROUP)||(type==DPSYS_SETPLAYERORGROUPDATA)))
  306. return E_FAIL;
  307. //read the pointer to BSTR
  308. if (m_nReadIndex >m_dwSize) return E_FAIL;
  309. pstr=*((WCHAR**)(m_pData+m_nReadIndex));
  310. //read the size
  311. m_nReadIndex=m_nReadIndex+sizeof(DWORD); //move on to the next arg if fail on a system message
  312. if (m_nReadIndex >m_dwSize) return E_FAIL;
  313. size= *((DWORD*)(m_pData+m_nReadIndex));
  314. __try {
  315. *ret=SysAllocString(pstr);
  316. }
  317. __except(1,1){
  318. return E_FAIL;
  319. }
  320. return S_OK;
  321. }
  322. HRESULT C_dxj_DirectPlayMessageObject::readSysMsgConnection( I_dxj_DPLConnection **ret)
  323. {
  324. //valid on DPSYS_STARTSESSION
  325. //make sure we have enough space to check the type
  326. if (m_dwSize<8) return E_FAIL;
  327. DWORD type= *((DWORD*)(m_pData));
  328. if (!(type==DPSYS_STARTSESSION)) return E_FAIL;
  329. DWORD dwConnection= *((DWORD*)(m_pData+sizeof(DWORD)));
  330. INTERNAL_CREATE_STRUCT(_dxj_DPLConnection,ret);
  331. if (!ret) return E_OUTOFMEMORY;
  332. HRESULT hr=(*ret)->setConnectionStruct( dwConnection);
  333. return hr;
  334. }
  335. HRESULT C_dxj_DirectPlayMessageObject::readSysMsgSessionDesc( I_dxj_DirectPlaySessionData **ret)
  336. {
  337. //valid on DPSYS_SETSESSIONDESC
  338. //make sure we have enough space to check the type
  339. if (m_dwSize<8) return E_FAIL;
  340. DWORD type= *((DWORD*)(m_pData));
  341. if (!(type==DPSYS_SETSESSIONDESC)) return E_FAIL;
  342. DPSESSIONDESC2 *pDesc= (LPDPSESSIONDESC2) *((DWORD*)(m_pData+sizeof(DWORD)));
  343. HRESULT hr=C_dxj_DirectPlaySessionDataObject::create(pDesc,ret);
  344. return hr;
  345. }
  346. HRESULT C_dxj_DirectPlayMessageObject::readSysChatString( BSTR *ret)
  347. {
  348. //valid on DPSYS_CHAT.
  349. //make sure we have enough space to check the type
  350. if (m_dwSize<40) return E_FAIL;
  351. DWORD type= *((DWORD*)(m_pData));
  352. if (!(type==DPSYS_CHAT)) return E_FAIL;
  353. DPMSG_CHAT *pChatMsg = (DPMSG_CHAT*)m_pData;
  354. __try{
  355. *ret = SysAllocString(pChatMsg->lpChat->lpszMessage);
  356. }
  357. __except(1,1){
  358. return E_FAIL;
  359. }
  360. return S_OK;
  361. }
  362. HRESULT C_dxj_DirectPlayMessageObject::moveToSecureMessage()
  363. {
  364. //valid on DPSYS_CHAT.
  365. //make sure we have enough space to check the type
  366. if (m_dwSize<18) return E_FAIL;
  367. DWORD type= *((DWORD*)(m_pData));
  368. if (!(type==DPSYS_SECUREMESSAGE)) return E_FAIL;
  369. DPMSG_SECUREMESSAGE *pMsg = (DPMSG_SECUREMESSAGE*)m_pData;
  370. DWORD newIndex=0;
  371. __try{
  372. newIndex= ((DWORD)pMsg->lpData)-((DWORD)m_pData);
  373. }
  374. __except(1,1)
  375. {
  376. return E_FAIL;
  377. }
  378. if (newIndex >m_dwSize) return E_FAIL;
  379. m_nReadIndex=newIndex;
  380. return S_OK;
  381. }