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.

210 lines
4.7 KiB

  1. // menucmd.cpp - Context menu command class
  2. #include "stdafx.h"
  3. #include "menucmd.h"
  4. #include "streamio.h"
  5. #include "qryitem.h"
  6. #include "resource.h"
  7. #include <shellapi.h>
  8. #include <algorithm>
  9. #include <atlgdi.h>
  10. extern DWORD g_dwFileVer; // Current console file version (from compdata.cpp)
  11. // Table of standard menu command parameters
  12. // Gives order for parameter menu and maps ID to resource string
  13. // Zero entry indicates menu separator
  14. const MENU_PARAM_ENTRY MenuParamTable[MENU_PARAM_TABLE_LEN] =
  15. {
  16. { MENU_PARAM_SCOPE, IDS_QUERY_SCOPE },
  17. { MENU_PARAM_FILTER, IDS_QUERY_FILTER },
  18. { MENU_PARAM_ID(0), 0 },
  19. { MENU_PARAM_NAME, IDS_NAME },
  20. { MENU_PARAM_TYPE, IDS_TYPE },
  21. };
  22. /////////////////////////////////////////////////////////////////////////////////////////
  23. // CShellMenuCmd
  24. HRESULT
  25. CShellMenuCmd::Save(IStream& stm)
  26. {
  27. stm << m_menuID;
  28. stm << m_dwFlags;
  29. stm << m_strProgPath;
  30. stm << m_strCmdLine;
  31. stm << m_strStartDir;
  32. stm << m_guidNoLocMenu;
  33. return S_OK;
  34. }
  35. HRESULT
  36. CShellMenuCmd::Load(IStream& stm)
  37. {
  38. stm >> m_menuID;
  39. if (g_dwFileVer >= 101)
  40. stm >> m_dwFlags;
  41. stm >> m_strProgPath;
  42. stm >> m_strCmdLine;
  43. stm >> m_strStartDir;
  44. if( g_dwFileVer >= 150 )
  45. {
  46. stm >> m_guidNoLocMenu;
  47. }
  48. return S_OK;
  49. }
  50. HRESULT
  51. CShellMenuCmd::Execute(CParamLookup* pLookup, HANDLE* phProcess)
  52. {
  53. ASSERT(pLookup != NULL && phProcess != NULL);
  54. *phProcess = NULL;
  55. // Substitue parameter values in the command line
  56. tstring strParam = m_strCmdLine;
  57. HRESULT hr = ReplaceParameters(strParam, *pLookup, FALSE);
  58. RETURN_ON_FAILURE(hr);
  59. // Expand any environment variables
  60. tstring strLocProgPath;
  61. hr = ExpandEnvironmentParams(m_strProgPath, strLocProgPath);
  62. RETURN_ON_FAILURE(hr);
  63. tstring strLocStartDir;
  64. hr = ExpandEnvironmentParams(m_strStartDir, strLocStartDir);
  65. RETURN_ON_FAILURE(hr);
  66. tstring strLocParam;
  67. ExpandEnvironmentParams(strParam, strLocParam);
  68. RETURN_ON_FAILURE(hr);
  69. // Execute the command
  70. SHELLEXECUTEINFO info;
  71. info.cbSize = sizeof(info);
  72. info.fMask = SEE_MASK_NOCLOSEPROCESS;
  73. info.hwnd = NULL;
  74. info.lpVerb = NULL;
  75. info.lpFile = strLocProgPath.c_str();
  76. info.lpParameters = strLocParam.c_str();
  77. info.lpDirectory = strLocStartDir.c_str();
  78. info.nShow = SW_SHOWNORMAL;
  79. info. hInstApp = 0;
  80. info.hProcess = 0;
  81. *phProcess = info.hProcess;
  82. BOOL bStat = ShellExecuteEx(&info);
  83. if (!bStat)
  84. return E_FAIL;
  85. *phProcess = info.hProcess;
  86. return S_OK;
  87. }
  88. /////////////////////////////////////////////////////////////////////////////////////////
  89. // CActDirMenuCmd
  90. HRESULT
  91. CActDirMenuCmd::Save(IStream& stm)
  92. {
  93. stm << m_menuID;
  94. stm << m_dwFlags;
  95. stm << m_strADName;
  96. stm << m_guidNoLocMenu;
  97. stm << m_strADNoLocName;
  98. return S_OK;
  99. }
  100. HRESULT
  101. CActDirMenuCmd::Load(IStream& stm)
  102. {
  103. stm >> m_menuID;
  104. if (g_dwFileVer >= 101)
  105. stm >> m_dwFlags;
  106. stm >> m_strADName;
  107. if( g_dwFileVer >= 150 )
  108. {
  109. stm >> m_guidNoLocMenu;
  110. stm >> m_strADNoLocName;
  111. }
  112. return S_OK;
  113. }
  114. //////////////////////////////////////////////////////////////////////
  115. // menu vector stream i/o
  116. IStream& operator<< (IStream& stm, menucmd_vector& vMenus)
  117. {
  118. stm << static_cast<long>(vMenus.size());
  119. menucmd_vector::iterator itMenu;
  120. for (itMenu = vMenus.begin(); itMenu != vMenus.end(); ++itMenu)
  121. {
  122. stm << static_cast<int>((*itMenu)->MenuType());
  123. HRESULT hr = (*itMenu)->Save(stm);
  124. THROW_ON_FAILURE(hr);
  125. }
  126. return stm;
  127. }
  128. IStream& operator>> (IStream& stm, menucmd_vector& vMenus)
  129. {
  130. long nItems;
  131. stm >> nItems;
  132. vMenus.reserve(nItems);
  133. for (long lItem = 0; lItem < nItems; ++lItem)
  134. {
  135. CMenuCmd* pMenu = NULL;
  136. int iType;
  137. stm >> iType;
  138. MENUTYPE type = static_cast<MENUTYPE>(iType);
  139. switch (type)
  140. {
  141. case MENUTYPE_SHELL:
  142. pMenu = new CShellMenuCmd();
  143. ASSERT(pMenu != NULL);
  144. break;
  145. case MENUTYPE_ACTDIR:
  146. pMenu = new CActDirMenuCmd();
  147. ASSERT(pMenu != NULL);
  148. break;
  149. default:
  150. THROW_ON_FAILURE(E_FAIL);
  151. }
  152. if( pMenu )
  153. {
  154. HRESULT hr = pMenu->Load(stm);
  155. THROW_ON_FAILURE(hr);
  156. vMenus.push_back(CMenuCmdPtr(pMenu));
  157. }
  158. }
  159. return stm;
  160. }