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

Windows编程

开发平台:

Visual C++

  1. /*
  2.  *  REGDB.C
  3.  *
  4.  *  Functions to query the registration database
  5.  *
  6.  *  OleStdGetMiscStatusOfClass
  7.  *  OleStdGetDefaultFileFormatOfClass
  8.  *  OleStdGetAuxUserType
  9.  *  OleStdGetUserTypeOfClass
  10.  *
  11.  *    (c) Copyright Microsoft Corp. 1992-1996 All Rights Reserved
  12.  *
  13.  */
  14. #define STRICT  1
  15. #include "olestd.h"
  16. #include "common.h"
  17. #include <ctype.h>
  18. OLEDBGDATA
  19. // Replacement for stdlib atol,
  20. // which didn't work and doesn't take far pointers.
  21. // Must be tolerant of leading spaces.
  22. //
  23. //
  24. static LONG Atol(LPSTR lpsz)
  25. {
  26.    signed int sign = +1;
  27.    UINT base = 10;
  28.    LONG l = 0;
  29.    if (NULL==lpsz)
  30.    {
  31.       OleDbgAssert (0);
  32.       return 0;
  33.    }
  34.    while (isspace(*lpsz))
  35.       lpsz++;
  36.    if (*lpsz=='-')
  37.    {
  38.       lpsz++;
  39.       sign = -1;
  40.    }
  41.    if (lpsz[0]=='0' && lpsz[1]=='x')
  42.    {
  43.       base = 16;
  44.       lpsz+=2;
  45.    }
  46.    if (base==10)
  47.    {
  48.       while (isdigit(*lpsz))
  49.       {
  50.          l = l * base + *lpsz - '0';
  51.          lpsz++;
  52.       }
  53.    }
  54.    else
  55.    {
  56.       OleDbgAssert (base==16);
  57.       while (isxdigit(*lpsz))
  58.       {
  59.          l = l * base + isdigit(*lpsz) ? *lpsz - '0' : toupper(*lpsz) - 'A' + 10;
  60.          lpsz++;
  61.       }
  62.    }
  63.    return l * sign;
  64. }
  65. /*
  66.  * OleStdGetUserTypeOfClass(REFCLSID, LPSTR, UINT, HKEY)
  67.  *
  68.  * Purpose:
  69.  *  Returns the user type (human readable class name) of the specified class.
  70.  *
  71.  * Parameters:
  72.  *  rclsid          pointer to the clsid to retrieve user type of.
  73.  *  lpszUserType    pointer to buffer to return user type in.
  74.  *  cch             length of buffer pointed to by lpszUserType
  75.  *  hKey            hKey for reg db - if this is NULL, then we
  76.  *                   open and close the reg db within this function.  If it
  77.  *                   is non-NULL, then we assume it's a valid key to the
  78.  *                    root and use it without closing it. (useful
  79.  *                   if you're doing lots of reg db stuff).
  80.  *
  81.  * Return Value:
  82.  *  UINT            Number of characters in returned string.  0 on error.
  83.  *
  84.  */
  85. STDAPI_(UINT) OleStdGetUserTypeOfClass(REFCLSID rclsid, LPOLESTR lpszUserType, UINT cch, HKEY hKey)
  86. {
  87.    LONG     dw;
  88.    LONG     lRet;
  89.    LPOLESTR lpszCLSID, lpszProgID;
  90.    char     lpszAnsiCLSID[256], lpszAnsiProgID[256];
  91.    BOOL     fFreeProgID = FALSE;
  92.    BOOL     bCloseRegDB = FALSE;
  93.    char     szKey[128];
  94.    LPMALLOC lpIMalloc;
  95.    char     lpszAnsiUserType[256];
  96.    if (!lpszUserType)
  97.       return 0;
  98.    *lpszUserType = '';
  99.    if (hKey == NULL)
  100.    {
  101.     //Open up the root key.
  102.     lRet=RegOpenKey(HKEY_CLASSES_ROOT, NULL, &hKey);
  103.     if ((LONG)ERROR_SUCCESS!=lRet)
  104.       return (UINT)FALSE;
  105.     bCloseRegDB = TRUE;
  106.    }
  107.    // Get a string containing the class name
  108.    StringFromCLSID(rclsid, &lpszCLSID);
  109.    W2A (lpszCLSID, lpszAnsiCLSID, 256);
  110.    wsprintf(szKey, "CLSID\%s", lpszAnsiCLSID);
  111.    dw=cch;
  112.    lRet = RegQueryValue(hKey, szKey, lpszAnsiUserType, &dw);
  113.    A2W (lpszAnsiUserType, lpszUserType, cch);
  114.    if ((LONG)ERROR_SUCCESS!=lRet) {
  115.       // Load 'Unknown Source' and 'Unknown Type' strings
  116.       dw = (LONG)LoadString(ghInst, (UINT)IDS_PSUNKNOWNTYPE, lpszAnsiUserType, cch);
  117.       A2W (lpszAnsiUserType, lpszUserType, cch);
  118.    }
  119.    if ( ((LONG)ERROR_SUCCESS!=lRet) && (CoIsOle1Class(rclsid)) )
  120.    {
  121.      // We've got an OLE 1.0 class, so let's try to get the user type
  122.      // name from the ProgID entry.
  123.      ProgIDFromCLSID(rclsid, &lpszProgID);
  124.      fFreeProgID = TRUE;
  125.      dw = cch;
  126.      W2A (lpszProgID, lpszAnsiProgID, 256);
  127.      lRet = RegQueryValue(hKey, lpszAnsiProgID, lpszAnsiUserType, &dw);
  128.      A2W (lpszAnsiUserType, lpszUserType, cch);
  129.      if ((LONG)ERROR_SUCCESS != lRet)
  130.       dw = 0;
  131.    }
  132.    if (NOERROR == CoGetMalloc(MEMCTX_TASK, &lpIMalloc))
  133.    {
  134.       if (fFreeProgID)
  135.        lpIMalloc->lpVtbl->Free(lpIMalloc, (LPVOID)lpszProgID);
  136.       lpIMalloc->lpVtbl->Free(lpIMalloc, (LPVOID)lpszCLSID);
  137.       lpIMalloc->lpVtbl->Release(lpIMalloc);
  138.    }
  139.    if (bCloseRegDB)
  140.      RegCloseKey(hKey);
  141.    return (UINT)dw;
  142. }
  143. /*
  144.  * OleStdGetAuxUserType(RCLSID, WORD, LPSTR, int, HKEY)
  145.  *
  146.  * Purpose:
  147.  *  Returns the specified AuxUserType from the reg db.
  148.  *
  149.  * Parameters:
  150.  *  rclsid          pointer to the clsid to retrieve aux user type of.
  151.  *  hKey            hKey for reg db - if this is NULL, then we
  152.  *                   open and close the reg db within this function.  If it
  153.  *                   is non-NULL, then we assume it's a valid key to the
  154.  *                    root and use it without closing it. (useful
  155.  *                   if you're doing lots of reg db stuff).
  156.  *  wAuxUserType    which aux user type field to look for.  In 4/93 release
  157.  *                  2 is short name and 3 is exe name.
  158.  *  lpszUserType    pointer to buffer to return user type in.
  159.  *  cch             length of buffer pointed to by lpszUserType
  160.  *
  161.  * Return Value:
  162.  *  UINT            Number of characters in returned string.  0 on error.
  163.  *
  164.  */
  165. STDAPI_(UINT) OleStdGetAuxUserType(REFCLSID rclsid,
  166.                            WORD     wAuxUserType,
  167.                            LPOLESTR lpszAuxUserType,
  168.                            int      cch,
  169.                            HKEY     hKey)
  170. {
  171.    HKEY     hThisKey;
  172.    BOOL     fCloseRegDB = FALSE;
  173.    LONG     dw;
  174.    LRESULT  lRet;
  175.    LPOLESTR lpszCLSID;
  176.    char     lpszAnsiCLSID[256];
  177.    char     lpszAnsiAuxUserType[256];
  178.    LPMALLOC lpIMalloc;
  179.    char     szKey[OLEUI_CCHKEYMAX];
  180.    char     szTemp[32];
  181.    lpszAnsiAuxUserType[0] = '';
  182.    if (NULL == hKey)
  183.    {
  184.      lRet = RegOpenKey(HKEY_CLASSES_ROOT, NULL, &hThisKey);
  185.      if (ERROR_SUCCESS != lRet)
  186.         return 0;
  187.    }
  188.    else
  189.      hThisKey = hKey;
  190.    StringFromCLSID(rclsid, &lpszCLSID);
  191.    W2A (lpszCLSID, lpszAnsiCLSID, 256);
  192.    lstrcpy(szKey, "CLSID\");
  193.    lstrcat(szKey, lpszAnsiCLSID);
  194.    wsprintf(szTemp, "\AuxUserType\%d", wAuxUserType);
  195.    lstrcat(szKey, szTemp);
  196.    dw = cch;
  197.    lRet = RegQueryValue(hThisKey, szKey, lpszAnsiAuxUserType, &dw);
  198.    if (ERROR_SUCCESS != lRet) {
  199.     dw = 0;
  200.     lpszAuxUserType[0] = '';
  201.    }
  202.    if (fCloseRegDB)
  203.      RegCloseKey(hThisKey);
  204.    if (NOERROR == CoGetMalloc(MEMCTX_TASK, &lpIMalloc))
  205.    {
  206.       lpIMalloc->lpVtbl->Free(lpIMalloc, (LPVOID)lpszCLSID);
  207.       lpIMalloc->lpVtbl->Release(lpIMalloc);
  208.    }
  209.    A2W (lpszAnsiAuxUserType, lpszAuxUserType, cch);
  210.    return (UINT)dw;
  211. }
  212. /*
  213.  * OleStdGetMiscStatusOfClass(REFCLSID, HKEY)
  214.  *
  215.  * Purpose:
  216.  *  Returns the value of the misc status for the given clsid.
  217.  *
  218.  * Parameters:
  219.  *  rclsid          pointer to the clsid to retrieve user type of.
  220.  *  hKey            hKey for reg db - if this is NULL, then we
  221.  *                   open and close the reg db within this function.  If it
  222.  *                   is non-NULL, then we assume it's a valid key to the
  223.  *                   \CLSID root and use it without closing it. (useful
  224.  *                   if you're doing lots of reg db stuff).
  225.  *
  226.  * Return Value:
  227.  *  BOOL            TRUE on success, FALSE on failure.
  228.  *
  229.  */
  230. STDAPI_(BOOL) OleStdGetMiscStatusOfClass(REFCLSID rclsid, HKEY hKey, DWORD FAR * lpdwValue)
  231. {
  232.    DWORD dw;
  233.    LONG  lRet;
  234.    LPOLESTR lpszCLSID;
  235.    char     lpszAnsiCLSID[256];
  236.    char  szKey[64];
  237.    char  szMiscStatus[OLEUI_CCHKEYMAX];
  238.    BOOL  bCloseRegDB = FALSE;
  239.    if (hKey == NULL)
  240.    {
  241.     //Open up the root key.
  242.     lRet=RegOpenKey(HKEY_CLASSES_ROOT, "CLSID", &hKey);
  243.     if ((LONG)ERROR_SUCCESS!=lRet)
  244.       return FALSE;
  245.     bCloseRegDB = TRUE;
  246.    }
  247.    // Get a string containing the class name
  248.    StringFromCLSID(rclsid, &lpszCLSID);
  249.    W2A (lpszCLSID, lpszAnsiCLSID, 256);
  250.    // Construct key
  251.    lstrcpy(szKey, lpszAnsiCLSID);
  252.    lstrcat(szKey, "\MiscStatus");
  253.    dw=OLEUI_CCHKEYMAX;
  254.    lRet = RegQueryValue(hKey, szKey, /*(LPSTR)*/szMiscStatus, &dw);
  255.    if ((LONG)ERROR_SUCCESS!=lRet)
  256.    {
  257.       OleStdFreeString(lpszCLSID, NULL);
  258.       if (bCloseRegDB)
  259.         RegCloseKey(hKey);
  260.       return FALSE;
  261.    }
  262.    *lpdwValue = Atol(/*(LPSTR)*/szMiscStatus);
  263.    OleStdFreeString(lpszCLSID, NULL);
  264.    if (bCloseRegDB)
  265.      RegCloseKey(hKey);
  266.    return TRUE;
  267. }
  268. /*
  269.  * CLIPFORMAT OleStdGetDefaultFileFormatOfClass(REFCLSID, HKEY)
  270.  *
  271.  * Purpose:
  272.  *  Returns the default file format of the specified class.
  273.  *  this is entered in REGDB as follows:
  274.  *      CLSID{...}DataFormatsDefaultFile = <cfFmt>
  275.  *
  276.  * Parameters:
  277.  *  rclsid          pointer to the clsid to retrieve user type of.
  278.  *  hKey            hKey for reg db- if this is NULL, then we
  279.  *                   open and close the reg db within this function.  If it
  280.  *                   is non-NULL, then we assume it's a valid key to the
  281.  *                    root and use it without closing it. (useful
  282.  *                   if you're doing lots of reg db stuff).
  283.  *
  284.  * Return Value:
  285.  *  cfFmt   -- DefaultFile format
  286.  *  NULL    -- failed to get default file format
  287.  *
  288.  */
  289. STDAPI_(CLIPFORMAT) OleStdGetDefaultFileFormatOfClass(
  290.       REFCLSID        rclsid,
  291.       HKEY            hKey
  292. )
  293. {
  294.    CLIPFORMAT cfFmt = 0;
  295.    DWORD dw;
  296.    LONG  lRet;
  297.    LPOLESTR lpszCLSID;
  298.    char     lpszAnsiCLSID[256];
  299.    BOOL  bCloseRegDB = FALSE;
  300.    char  szKey[128];
  301.    char  szDefaultFile[OLEUI_CCHKEYMAX];
  302.    BOOL  bStatus = TRUE;
  303.    if (hKey == NULL)
  304.    {
  305.     //Open up the root key.
  306.     lRet=RegOpenKey(HKEY_CLASSES_ROOT, NULL, &hKey);
  307.     if ((LONG)ERROR_SUCCESS!=lRet)
  308.       return 0;
  309.     bCloseRegDB = TRUE;
  310.    }
  311.    // Get a string containing the class name
  312.    StringFromCLSID(rclsid, &lpszCLSID);
  313.    W2A (lpszCLSID, lpszAnsiCLSID, 256);
  314.    // Construct key
  315.    wsprintf(szKey, "CLSID\%s\DataFormats\DefaultFile", lpszCLSID);
  316.    OleStdFreeString(lpszCLSID, NULL);
  317.    dw=OLEUI_CCHKEYMAX;
  318.    lRet = RegQueryValue(hKey, szKey, /*(LPSTR)*/szDefaultFile, (LONG FAR *)&dw);
  319.    if ((LONG)ERROR_SUCCESS!=lRet)
  320.       bStatus = FALSE;
  321.    else {
  322.       /* if the format is a number, then it should refer to one of the
  323.       **    standard Windows formats.
  324.       */
  325.       if (isdigit(szDefaultFile[0]))
  326.          cfFmt = (CLIPFORMAT)Atol(szDefaultFile);
  327.       else
  328.          cfFmt = RegisterClipboardFormat(szDefaultFile);
  329.    }
  330.    if (bCloseRegDB)
  331.      RegCloseKey(hKey);
  332.    return cfFmt;
  333. }