STANDARD.C
上传用户:bangxh
上传日期:2007-01-31
资源大小:42235k
文件大小:11k
源码类别:

Windows编程

开发平台:

Visual C++

  1. //*---------------------------------------------------------------------------------
  2. //|  ODBC System Administrator
  3. //|
  4. //|  This code is furnished on an as-is basis as part of the ODBC SDK and is
  5. //|  intended for example purposes only.
  6. //|
  7. //|   Title:   STANDARD.C
  8. //|      This module contains standard functions which can be used by many
  9. //|      different tools.
  10. //|
  11. //|      The DumpDebugInfo function when enabled will cause all memory requests
  12. //|      and frees to be written to a comma separated file.  This file can then
  13. //|      be queries via the sample Text ODBC Driver to find memory problems.
  14. //*---------------------------------------------------------------------------------
  15. #include "standard.h"
  16. #include <windowsx.h>
  17. #include <string.h>
  18. #include <stdlib.h>
  19. #include <stdio.h>
  20. #include <stdarg.h>
  21. #include "errcheck.h"
  22. #include "strings.h"
  23. //*---------------------------------------------------------------------------------
  24. //|   Global variables
  25. //*---------------------------------------------------------------------------------
  26. char OutStr[MAXBUFF];
  27. dCSEG(char) szui[]                        =  "%u";
  28. dCSEG(char) szEmpty[]                     =  "";
  29. dCSEG(char) szcrlf[]                      =  "rn";
  30. #ifdef _DEBUG
  31. #include "time.h"
  32. #define szASSERTERROR (LPSTR)"Assert: %s, %s, %d"
  33. #define szDEBUGFILE (LPSTR)"C:\TMP\MEM"
  34. char szDbgOut[200];
  35. BOOL fNew=TRUE;
  36. void WinAssertReal(int exp, LPSTR msg, LPSTR file, int line)
  37. {
  38.    if(!exp) {
  39.       wsprintf(szDbgOut, szASSERTERROR, msg, file, line);
  40.       MessageBox(GetActiveWindow(), szDbgOut, szErrTitle, MB_OK);
  41.    }
  42. }
  43. void DumpDebugInfo(LPVOID tmp, LPSTR szFile, int cbLine, int stat,
  44.          DWORD rqSize, DWORD aSize)
  45. {
  46.    static   OFSTRUCT    ofs;
  47.    static   HFILE       hf;
  48.    static   time_t      thetime;
  49.    static   struct tm * tmVal;
  50.    if(fNew) {
  51.       fNew = FALSE;
  52.       ofs.cBytes = sizeof(OFSTRUCT);
  53.       hf = OpenFile(szDEBUGFILE, &ofs, OF_DELETE);
  54.       _lclose(hf);
  55.    }
  56.    // Creates file MEM which is a comma separated text file.
  57.    // Issue the select statement to find memory ptrs
  58.    // which were allocated but never freed (status=1), and
  59.    // pointers which were freed but never allocated (status=-1).
  60.    // Of course "No data found" is the desired response.
  61.    //    create table mem
  62.    //        (address char(9),
  63.    //         logtime char(8),
  64.    //         status integer,
  65.    //         desired integer,
  66.    //         actual integer,
  67.    //         line integer,
  68.    //         file char(45))
  69.    //    select address, sum(status) from mem
  70.    //      group by address having sum(status) <> 0
  71.    time(&thetime);
  72.    tmVal = localtime(&thetime);
  73.    wsprintf(szDbgOut, (LPSTR)"%04X:%04X,%02u:%02u:%02u,%d,%lu,%lu,%u,%srn",
  74.             HIWORD(tmp), LOWORD(tmp), tmVal->tm_hour, tmVal->tm_min, tmVal->tm_sec,
  75.             stat, rqSize, aSize, cbLine, (LPSTR)szFile);
  76.    if((hf = _lopen(szDEBUGFILE, WRITE)) == -1)  // File not found
  77.       hf = OpenFile(szDEBUGFILE, &ofs, OF_CREATE);
  78.    _llseek(hf, 0L, 2);                    // Try to go to end of file
  79.    _lwrite(hf, szDbgOut, lstrlen(szDbgOut));  // Write wherever we are
  80.    _lclose(hf);
  81. }
  82. void FAR * DebugGetMemory(DWORD size, LPSTR szFile, int cbLine)
  83. {
  84.    LPVOID   ptr;
  85.    DWORD    aSize;
  86.    ptr = DoGetMemory(size);
  87.    if(!ptr)
  88.       return ptr;
  89.    aSize = GlobalSize(GlobalPtrHandle(ptr));
  90.    DumpDebugInfo(ptr, szFile, cbLine, 1, size, aSize);
  91.    return ptr;
  92. }
  93. void DebugReleaseMemory(LPVOID ptr, LPSTR szFile, int cbLine)
  94. {
  95.    GlobalFreePtr(ptr);
  96.    DumpDebugInfo(ptr, szFile, cbLine, -1, 0, 0);
  97. }
  98. #endif      // Debug memory routines
  99. //*---------------------------------------------------------------------------------
  100. //| DoGetMemory:
  101. //|   This function allocates the specified amount of memory.
  102. //| Parms:
  103. //|   in       size                 How much memory
  104. //| Returns:
  105. //|   Long pointer to void
  106. //*---------------------------------------------------------------------------------
  107. void FAR * DoGetMemory(DWORD size)
  108. {
  109.    LPVOID   tmp;
  110.    tmp = GlobalAllocPtr(GMEM_FIXED | GMEM_ZEROINIT, size);
  111.    if(!tmp)
  112.       szMessageBox(GetActiveWindow(),
  113.                    MB_ICONEXCLAMATION,
  114.                    (LPSTR)szErrTitle,
  115.                    GetidsString(idsOutOfMemory, OutStr, MAXBUFF));
  116.    return tmp;
  117. }
  118. //*---------------------------------------------------------------------------------
  119. //| DoReleaseMemory:
  120. //|   Free up the memory we have requested
  121. //| Parms:
  122. //|   ptr         The pointer to free
  123. //| Returns:
  124. //|   Nothing.
  125. //*---------------------------------------------------------------------------------
  126. void DoReleaseMemory(LPVOID ptr)
  127. {
  128.    GlobalFreePtr(ptr);
  129. }
  130. //*---------------------------------------------------------------------------------
  131. //| RemoveCrLf:
  132. //|   This will remove all carriage return/line feeds from the input buffer.
  133. //| Parms:
  134. //|   in       instr                Null terminated string
  135. //| Returns:
  136. //|   Nothing
  137. //*---------------------------------------------------------------------------------
  138. void RemoveCrLf(LPSTR instr)
  139. {
  140.    LPSTR str=instr;
  141.    if(!str ||
  142.       !*str)
  143.       return;
  144.    while((str = _fstrstr(str, (LPSTR)szcrlf))) {
  145.       *str++ = ' ';
  146.       *str++ = ' ';
  147.    }
  148. }
  149. //*---------------------------------------------------------------------------------
  150. //| GetNewDirectory:
  151. //|   This function will take a complete file name (must have path included)
  152. //|   and return only the path portion with no trailing ''
  153. //| Parms:
  154. //|   outstr            Output path name with no file
  155. //|   instr             Input complete file name
  156. //| Returns:
  157. //|   Nothing
  158. //*---------------------------------------------------------------------------------
  159. void GetNewDirectory(LPSTR outstr, LPSTR instr)
  160. {
  161.    LPSTR    str=outstr;
  162.    LPSTR    lstr=outstr;
  163.    lstrcpy(str, instr);
  164.    while((str = _fstrchr(lstr+1, '\')))
  165.       lstr = str++;
  166.    *++lstr = '';
  167. }
  168. //*---------------------------------------------------------------------------------
  169. //| ValidName:
  170. //|   This function parses a string to look for invalid characters which would
  171. //|   preclude it from being written as a section or entry in an .ini file.
  172. //| Parms:
  173. //|   instr             Input complete file name
  174. //| Returns:
  175. //|   TRUE if it is valid, FALSE on error
  176. //*---------------------------------------------------------------------------------
  177. BOOL ValidName(LPSTR instr)
  178. {
  179.    LPSTR str=instr;
  180.    if(!str)
  181.       return TRUE;
  182.    while(*str)
  183.       switch(*str) {
  184.         case '[':
  185.         case ']':
  186.         case '=':
  187.          return FALSE;
  188.         default:
  189.          ++str;
  190.       }
  191.    return TRUE;
  192. }
  193. //*---------------------------------------------------------------------------------
  194. //| lpatoi:
  195. //|   atoi only works for NEAR host vars, which makes it useless in a large
  196. //|   application.  This function tricks atoi by copy the long string to a
  197. //|   local variable and then doing the conversion.  This is a major cluge,
  198. //|   but a necessary one.
  199. //| Parms:
  200. //|   instr             Input number
  201. //| Returns:
  202. //|   The integer value of instr
  203. //*---------------------------------------------------------------------------------
  204. int lpatoi(LPSTR instr)
  205. {
  206.    char szStr[35];
  207.    lstrcpy((LPSTR)szStr, instr);
  208.    return atoi(szStr);
  209. }
  210. //*------------------------------------------------------------------------
  211. //|  GetidsString:
  212. //|      Will retrieve a string from our resource fork given the id.
  213. //|  Parms:
  214. //|      ids            The id of the string
  215. //|      szOut          Output buffer for string
  216. //|      cbSize         How big is the buffer
  217. //|  Returns:
  218. //|      Pointer to szOut
  219. //*------------------------------------------------------------------------
  220. LPSTR EXTFUN GetidsString(UINT ids, LPSTR szOut, UINT cbSize)
  221. {
  222.    extern HINSTANCE hInst;
  223.    if(!szOut)
  224.       return NULL;
  225.    if(!LoadString(hInst, ids, szOut, cbSize))
  226.       lstrcpy(szOut, "Not found");
  227.    return szOut;
  228. }
  229. //*------------------------------------------------------------------------
  230. //|  szWrite:
  231. //|      Allows you to format an output string which is then added
  232. //|      to the specified edit window.
  233. //|  Parms:
  234. //|      hwnd           Edit window for output
  235. //|      szFmt          Format string
  236. //|      (varying)      Arguements for format string
  237. //|  Returns:
  238. //|      Nothing
  239. //*------------------------------------------------------------------------
  240. VOID FAR CDECL szWrite(HWND hwnd, LPSTR szFmt, ...)
  241. {
  242. #define MAXEDITBUFF 30000
  243.    static      char  szBuffer[MAXBUFF];
  244.    UCHAR *     pszBuffer;
  245.    UCHAR       bufFmt[MAXBUFF];
  246.    va_list           marker;
  247.    UINT              rtn=0;
  248.    UINT              len=0;
  249.    pszBuffer = &szBuffer[0];
  250.    lstrcpy(bufFmt, szFmt);
  251.    // Use format and arguements as input
  252.    va_start(marker, szFmt);
  253.    if (_vsnprintf(pszBuffer, MAXBUFF, bufFmt, marker) < 0) {
  254.       wsprintf(pszBuffer,"Buffer overflow reporting '%*.*s'", 50,50,(LPSTR)szBuffer);
  255.       return;
  256.    }
  257.    va_end(marker);
  258.    // Now we have the string to add to the end of our output.  Verify that the
  259.    // new string will not be too large and set selection accordingly.
  260.    len = (UINT)SendMessage(hwnd, WM_GETTEXTLENGTH, 0, 0L);
  261.    if(len + lstrlen(pszBuffer) > MAXEDITBUFF) {    //  Need to truncate
  262.       SendMessage(hwnd, EM_SETSEL, 0, MAKELPARAM(0,len + 10));
  263.       SendMessage(hwnd, EM_REPLACESEL, 0, (LPARAM)((LPSTR)"...rn"));
  264.       SendMessage(hwnd, EM_SETSEL, 0, MAKELPARAM(len,len));
  265.    }
  266.    SendMessage(hwnd, EM_REPLACESEL, 0, (LPARAM)((LPSTR)pszBuffer));
  267. }
  268. //*------------------------------------------------------------------------
  269. //|  szMessageBox:
  270. //|      Works like sprintf only the output goes to a message box.
  271. //|  Parms:
  272. //|      hwnd           Owner window, NULL uses GetActiveWindow
  273. //|      style          Flags for MessageBox
  274. //|      szTitle        Title for message box
  275. //|      szFmt          Format string
  276. //|      (varying)      Arguements for format string
  277. //|  Returns:
  278. //|      Id from MessageBox
  279. //*------------------------------------------------------------------------
  280. int FAR CDECL szMessageBox(HWND hwnd, UINT style, LPSTR szTitle, LPSTR szFmt, ...)
  281. {
  282.    char        szBuffer[MAXBUFF];
  283.    char *      pszBuffer;
  284.    UCHAR       bufFmt[MAXBUFF];
  285.    va_list     marker;
  286.    pszBuffer = &szBuffer[0];
  287.    lstrcpy(bufFmt, szFmt);
  288.    // Use format and arguements as input
  289.    va_start(marker, szFmt);
  290.    if (_vsnprintf(pszBuffer, MAXBUFF, bufFmt, marker) < 0)
  291.       wsprintf(pszBuffer,"Buffer overflow reporting '%*.*s'", 50,50,szBuffer);
  292.    va_end(marker);
  293.    return(MessageBox((hwnd) ? hwnd : GetActiveWindow(),
  294.                      pszBuffer,
  295.                      szTitle,
  296.                      style) == IDOK);
  297. }