Source code of Windows XP (NT5)
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.

602 lines
10 KiB

  1. /*++
  2. Copyright (c) 1998-1999 Microsoft Corporation
  3. All rights reserved.
  4. Module Name:
  5. dbgutil.cxx
  6. Abstract:
  7. Debug Utility functions
  8. Author:
  9. Steve Kiraly (SteveKi) 24-May-1998
  10. Revision History:
  11. --*/
  12. #include "precomp.hxx"
  13. #pragma hdrstop
  14. DEBUG_NS_BEGIN
  15. /*++
  16. Title:
  17. ErrorText
  18. Routine Description:
  19. Function used to display an error text to the
  20. debugger. Just simplifies the task of formating
  21. a message string with sprintf.
  22. Arguments:
  23. pszFmt - pointer to sprintf format string.
  24. ... - variable number of arguments that matches format string.
  25. Return Value:
  26. TRUE message displayed, FALSE error occurred.
  27. --*/
  28. BOOL
  29. WINAPIV
  30. ErrorText(
  31. IN LPCTSTR pszFmt
  32. ...
  33. )
  34. {
  35. BOOL bReturn;
  36. if (Globals.DisplayLibraryErrors)
  37. {
  38. va_list pArgs;
  39. va_start( pArgs, pszFmt );
  40. TCHAR szBuffer[4096];
  41. bReturn = _vsntprintf( szBuffer, COUNTOF( szBuffer ), pszFmt, pArgs ) >= 0;
  42. if (bReturn)
  43. {
  44. OutputDebugString( szBuffer );
  45. }
  46. va_end( pArgs );
  47. }
  48. else
  49. {
  50. bReturn = TRUE;
  51. }
  52. return bReturn;
  53. }
  54. /*++
  55. Title:
  56. StripPathFromFileName
  57. Routine Description:
  58. Function used stip the path component from a fully
  59. qualified file name.
  60. Arguments:
  61. pszFile - pointer to full file name.
  62. Return Value:
  63. Pointer to start of file name in path.
  64. --*/
  65. LPCTSTR
  66. StripPathFromFileName(
  67. IN LPCTSTR pszFile
  68. )
  69. {
  70. LPCTSTR pszFileName;
  71. if (pszFile)
  72. {
  73. pszFileName = _tcsrchr( pszFile, _T('\\') );
  74. if (pszFileName)
  75. {
  76. pszFileName++;
  77. }
  78. else
  79. {
  80. pszFileName = pszFile;
  81. }
  82. }
  83. else
  84. {
  85. pszFileName = kstrNull;
  86. }
  87. return pszFileName;
  88. }
  89. /*++
  90. Title:
  91. GetProcessName
  92. Routine Description:
  93. Gets the current process short file name.
  94. Arguments:
  95. strProcessName - string reference where to return the process name.
  96. Return Value:
  97. TRUE success, FALSE error occurred.
  98. --*/
  99. BOOL
  100. GetProcessName(
  101. IN TDebugString &strProcessName
  102. )
  103. {
  104. BOOL bRetval = FALSE;
  105. LPCTSTR pszBuffer = NULL;
  106. TCHAR szBuffer[MAX_PATH];
  107. if( GetModuleFileName( NULL, szBuffer, COUNTOF( szBuffer ) ) )
  108. {
  109. pszBuffer = StripPathFromFileName( szBuffer );
  110. if( pszBuffer )
  111. {
  112. bRetval = strProcessName.bUpdate( pszBuffer );
  113. }
  114. }
  115. return bRetval;
  116. }
  117. /*++
  118. Title:
  119. bFormatA
  120. Routine Description:
  121. Formats a string and returns a heap allocated string with the
  122. formated data. This routine can be used to for extremely
  123. long format strings. Note: If a valid pointer is returned
  124. the callng functions must release the data with a call to delete.
  125. Example:
  126. LPSTR p = vFormatA( _T("Test %s"), pString );
  127. if (p)
  128. {
  129. SetTitle(p);
  130. }
  131. INTERNAL_DELETE [] p;
  132. Arguments:
  133. psFmt - format string
  134. pArgs - pointer to a argument list.
  135. Return Value:
  136. Pointer to formated string. NULL if error.
  137. --*/
  138. LPSTR
  139. vFormatA(
  140. IN LPCSTR pszFmt,
  141. IN va_list pArgs
  142. )
  143. {
  144. LPSTR pszBuff = NULL;
  145. INT iSize = 256;
  146. for( ; pszFmt; )
  147. {
  148. //
  149. // Allocate the message buffer.
  150. //
  151. pszBuff = INTERNAL_NEW CHAR [ iSize ];
  152. //
  153. // Allocating the buffer failed, we are done.
  154. //
  155. if (!pszBuff)
  156. {
  157. break;
  158. }
  159. //
  160. // Attempt to format the string. snprintf fails with a
  161. // negative number when the buffer is too small.
  162. //
  163. INT iLen = _vsnprintf( pszBuff, iSize, pszFmt, pArgs );
  164. //
  165. // snprintf does not null terminate the string if the buffer and the
  166. // final string are exactly the same length. If we detect this case
  167. // make the buffer larger and then call snprintf one extra time.
  168. //
  169. if (iLen > 0 && iLen != iSize)
  170. {
  171. break;
  172. }
  173. //
  174. // String did not fit release the current buffer.
  175. //
  176. INTERNAL_DELETE [] pszBuff;
  177. //
  178. // Null the buffer pointer.
  179. //
  180. pszBuff = NULL;
  181. //
  182. // Double the buffer size after each failure.
  183. //
  184. iSize *= 2;
  185. //
  186. // If the size is greater than 100k exit without formatting a string.
  187. //
  188. if (iSize > 100*1024)
  189. {
  190. break;
  191. }
  192. }
  193. return pszBuff;
  194. }
  195. /*++
  196. Title:
  197. bFormatW
  198. Routine Description:
  199. Formats a string and returns a heap allocated string with the
  200. formated data. This routine can be used to for extremely
  201. long format strings. Note: If a valid pointer is returned
  202. the callng functions must release the data with a call to delete.
  203. Example:
  204. LPWSTR p = vFormatW( _T("Test %s"), pString );
  205. if (p)
  206. {
  207. SetTitle(p);
  208. }
  209. INTERNAL_DELETE [] p;
  210. Arguments:
  211. psFmt - format string
  212. pArgs - pointer to a argument list.
  213. Return Value:
  214. Pointer to formated string. NULL if error.
  215. --*/
  216. LPWSTR
  217. vFormatW(
  218. IN LPCWSTR pszFmt,
  219. IN va_list pArgs
  220. )
  221. {
  222. LPWSTR pszBuff = NULL;
  223. INT iSize = 256;
  224. for( ; pszFmt; )
  225. {
  226. //
  227. // Allocate the message buffer.
  228. //
  229. pszBuff = INTERNAL_NEW WCHAR [ iSize ];
  230. //
  231. // Allocating the buffer failed, we are done.
  232. //
  233. if (!pszBuff)
  234. {
  235. break;
  236. }
  237. //
  238. // Attempt to format the string. snprintf fails with a
  239. // negative number when the buffer is too small.
  240. //
  241. INT iLen = _vsnwprintf( pszBuff, iSize, pszFmt, pArgs );
  242. //
  243. // snprintf does not null terminate the string if the buffer and the
  244. // final string are exactly the same length. If we detect this case
  245. // make the buffer larger and then call snprintf one extra time.
  246. //
  247. if (iLen > 0 && iLen != iSize)
  248. {
  249. break;
  250. }
  251. //
  252. // String did not fit release the current buffer.
  253. //
  254. INTERNAL_DELETE [] pszBuff;
  255. //
  256. // Null the buffer pointer.
  257. //
  258. pszBuff = NULL;
  259. //
  260. // Double the buffer size after each failure.
  261. //
  262. iSize *= 2;
  263. //
  264. // If the size is greater than 100k exit without formatting a string.
  265. //
  266. if (iSize > 100*1024)
  267. {
  268. break;
  269. }
  270. }
  271. return pszBuff;
  272. }
  273. /*++
  274. Title:
  275. StringConvert
  276. Routine Description:
  277. Convert an ansi string to a wide string returning
  278. a pointer to a newly allocated string.
  279. Arguments:
  280. ppResult - pointer to where to return pointer to new wide string.
  281. pString - pointer to ansi string.
  282. Return Value:
  283. TRUE success, FALSE error occurred.
  284. --*/
  285. BOOL
  286. StringConvert(
  287. IN OUT LPWSTR *ppResult,
  288. IN LPCSTR pString
  289. )
  290. {
  291. BOOL bReturn = FALSE;
  292. if( ppResult && pString )
  293. {
  294. INT iLen = strlen( pString ) + 1;
  295. *ppResult = INTERNAL_NEW WCHAR[iLen];
  296. if( *ppResult )
  297. {
  298. if( MultiByteToWideChar( CP_ACP, 0, pString, -1, *ppResult, iLen ) )
  299. {
  300. bReturn = TRUE;
  301. }
  302. else
  303. {
  304. INTERNAL_DELETE [] *ppResult;
  305. *ppResult = NULL;
  306. }
  307. }
  308. }
  309. return bReturn;
  310. }
  311. /*++
  312. Title:
  313. StringConvert
  314. Routine Description:
  315. Convert an ansi string to a heap allocated ansi string returning
  316. a pointer to a newly allocated string.
  317. Arguments:
  318. ppResult - pointer to where to return pointer to new ansi string.
  319. pString - pointer to ansi string.
  320. Return Value:
  321. TRUE success, FALSE error occurred.
  322. --*/
  323. BOOL
  324. StringConvert(
  325. IN OUT LPSTR *ppResult,
  326. IN LPCSTR pString
  327. )
  328. {
  329. BOOL bReturn = FALSE;
  330. if( ppResult && pString )
  331. {
  332. INT iLen = strlen( pString ) + 1;
  333. *ppResult = INTERNAL_NEW CHAR[iLen];
  334. if( *ppResult )
  335. {
  336. strcpy( *ppResult, pString );
  337. bReturn = TRUE;
  338. }
  339. }
  340. return bReturn;
  341. }
  342. /*++
  343. Title:
  344. StringConvert
  345. Routine Description:
  346. Convert a wide string to and ansi string returning
  347. a pointer to a newly allocated string.
  348. Arguments:
  349. ppResult - pointer to where to return pointer to new ansi string.
  350. pString - pointer to wide string.
  351. Return Value:
  352. TRUE success, FALSE error occurred.
  353. --*/
  354. BOOL
  355. StringConvert(
  356. IN OUT LPSTR *ppResult,
  357. IN LPCWSTR pString
  358. )
  359. {
  360. BOOL bReturn = FALSE;
  361. if( ppResult && pString )
  362. {
  363. INT iLen = wcslen( pString ) + 1;
  364. *ppResult = INTERNAL_NEW CHAR [iLen];
  365. if( *ppResult )
  366. {
  367. if( WideCharToMultiByte( CP_ACP, 0, pString, -1, *ppResult, iLen, NULL, NULL ) )
  368. {
  369. bReturn = TRUE;
  370. }
  371. else
  372. {
  373. INTERNAL_DELETE [] *ppResult;
  374. *ppResult = NULL;
  375. }
  376. }
  377. }
  378. return bReturn;
  379. }
  380. /*++
  381. Title:
  382. StringConvert
  383. Routine Description:
  384. Convert a wide string to and heap allocated wide string returning
  385. a pointer to a newly allocated string.
  386. Arguments:
  387. ppResult - pointer to where to return pointer to new wide string.
  388. pString - pointer to wide string.
  389. Return Value:
  390. TRUE success, FALSE error occurred.
  391. --*/
  392. BOOL
  393. StringConvert(
  394. IN OUT LPWSTR *ppResult,
  395. IN LPCWSTR pString
  396. )
  397. {
  398. BOOL bReturn = FALSE;
  399. if( ppResult && pString )
  400. {
  401. INT iLen = wcslen( pString ) + 1;
  402. *ppResult = INTERNAL_NEW WCHAR [iLen];
  403. if( *ppResult )
  404. {
  405. wcscpy( *ppResult, pString );
  406. bReturn = TRUE;
  407. }
  408. }
  409. return bReturn;
  410. }
  411. BOOL
  412. StringA2T(
  413. IN OUT LPTSTR *ppResult,
  414. IN LPCSTR pString
  415. )
  416. {
  417. return StringConvert( ppResult, pString );
  418. }
  419. BOOL
  420. StringT2A(
  421. IN OUT LPSTR *ppResult,
  422. IN LPCTSTR pString
  423. )
  424. {
  425. return StringConvert( ppResult, pString );
  426. }
  427. BOOL
  428. StringT2W(
  429. IN OUT LPWSTR *ppResult,
  430. IN LPCTSTR pString
  431. )
  432. {
  433. return StringConvert( ppResult, pString );
  434. }
  435. BOOL
  436. StringW2T(
  437. IN OUT LPTSTR *ppResult,
  438. IN LPCWSTR pString
  439. )
  440. {
  441. return StringConvert( ppResult, pString );
  442. }
  443. DEBUG_NS_END