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.

419 lines
10 KiB

  1. #ifndef __SSI_REQUEST_HXX__
  2. #define __SSI_REQUEST_HXX__
  3. /*++
  4. Copyright (c) 2001 Microsoft Corporation
  5. Module Name:
  6. ssi_request.hxx
  7. Abstract:
  8. This module contains the server side include processing code. We
  9. aim for support as specified by iis\spec\ssi.doc. The code is based
  10. on existing SSI support done in iis\svcs\w3\gateways\ssinc\ssinc.cxx.
  11. Master STM file handler ( STM file may include other files )
  12. Author:
  13. Ming Lu (MingLu) 5-Apr-2000
  14. Revision history
  15. Jaroslad Dec-2000
  16. - modified to execute asynchronously
  17. Jaroslad Apr-2001
  18. - added VectorSend support, keepalive, split to multiple source files
  19. --*/
  20. class SSI_INCLUDE_FILE;
  21. class SSI_ELEMENT_LIST;
  22. class SSI_FILE;
  23. /*++
  24. class SSI_REQUEST
  25. Master structure for SSI request.
  26. Provides a "library" of utilities for use by higher level functions
  27. Hierarchy:
  28. SSI_REQUEST
  29. - SSI_INCLUDE_FILE
  30. - SSI_FILE
  31. - SSI_ELEMENT_LIST
  32. --*/
  33. class SSI_REQUEST
  34. {
  35. public:
  36. ~SSI_REQUEST();
  37. VOID *
  38. operator new(
  39. size_t size
  40. )
  41. {
  42. UNREFERENCED_PARAMETER( size );
  43. // use ACACHE
  44. DBG_ASSERT( size == sizeof( SSI_REQUEST ) );
  45. DBG_ASSERT( sm_pachSsiRequests != NULL );
  46. return sm_pachSsiRequests->Alloc();
  47. }
  48. VOID
  49. operator delete(
  50. VOID * pSSIRequest
  51. )
  52. {
  53. DBG_ASSERT( pSSIRequest != NULL );
  54. DBG_ASSERT( sm_pachSsiRequests != NULL );
  55. DBG_REQUIRE( sm_pachSsiRequests->Free( pSSIRequest ) );
  56. }
  57. static
  58. HRESULT
  59. InitializeGlobals(
  60. VOID
  61. )
  62. /*++
  63. Routine Description:
  64. Global initialization routine for SSI_REQUEST
  65. Arguments:
  66. None
  67. Return Value:
  68. HRESULT
  69. --*/
  70. {
  71. ALLOC_CACHE_CONFIGURATION acConfig;
  72. HKEY hKeyParam;
  73. DWORD dwType;
  74. DWORD nBytes;
  75. DWORD dwValue;
  76. DWORD err;
  77. //
  78. // Setup allocation lookaside
  79. //
  80. acConfig.nConcurrency = 1;
  81. acConfig.nThreshold = 100;
  82. acConfig.cbSize = sizeof( SSI_REQUEST );
  83. DBG_ASSERT( sm_pachSsiRequests == NULL );
  84. sm_pachSsiRequests = new ALLOC_CACHE_HANDLER( "SSI_REQUEST",
  85. &acConfig );
  86. if ( sm_pachSsiRequests == NULL )
  87. {
  88. return HRESULT_FROM_WIN32( ERROR_NOT_ENOUGH_MEMORY );
  89. }
  90. if ( RegOpenKeyEx( HKEY_LOCAL_MACHINE,
  91. W3_PARAMETERS_KEY,
  92. 0,
  93. KEY_READ,
  94. &hKeyParam ) == NO_ERROR )
  95. {
  96. nBytes = sizeof( dwValue );
  97. err = RegQueryValueExA( hKeyParam,
  98. "SSIEnableCmdDirective",
  99. NULL,
  100. &dwType,
  101. ( LPBYTE )&dwValue,
  102. &nBytes
  103. );
  104. if ( ( err == ERROR_SUCCESS ) && ( dwType == REG_DWORD ) )
  105. {
  106. sm_fEnableCmdDirective = !!dwValue;
  107. }
  108. RegCloseKey( hKeyParam );
  109. }
  110. return NO_ERROR;
  111. }
  112. static
  113. VOID
  114. TerminateGlobals(
  115. VOID
  116. )
  117. /*++
  118. Routine Description:
  119. Terminate SSI_REQUEST globals
  120. Arguments:
  121. None
  122. Return Value:
  123. None
  124. --*/
  125. {
  126. if ( sm_pachSsiRequests != NULL )
  127. {
  128. delete sm_pachSsiRequests;
  129. sm_pachSsiRequests = NULL;
  130. }
  131. }
  132. static
  133. HRESULT
  134. CreateInstance(
  135. IN EXTENSION_CONTROL_BLOCK * pECB,
  136. OUT SSI_REQUEST ** ppSsiRequest
  137. );
  138. VOID
  139. SetCurrentIncludeFile(
  140. IN SSI_INCLUDE_FILE * pSIF
  141. )
  142. {
  143. _pSIF = pSIF;
  144. //
  145. // SSI_REQUEST takes ovnership
  146. // of all the child SSI_INCLUDE_FILE instances
  147. // That way sending the response data may be
  148. // delayed at the very end of the SSI_REQUEST handling
  149. //
  150. AddToDelayedSIFDeleteList( pSIF );
  151. }
  152. EXTENSION_CONTROL_BLOCK *
  153. GetECB(
  154. VOID
  155. ) const
  156. {
  157. return _pECB;
  158. }
  159. SSI_VECTOR_BUFFER&
  160. GetVectorBuffer(
  161. VOID
  162. )
  163. {
  164. return _VectorBuffer;
  165. }
  166. HANDLE
  167. GetUserToken(
  168. VOID
  169. )
  170. {
  171. return _hUser;
  172. }
  173. HRESULT
  174. SSISendError(
  175. IN DWORD dwMessageID,
  176. IN LPSTR apszParms[]
  177. );
  178. BOOL
  179. SetUserErrorMessage(
  180. IN STRA * pstrUserMessage
  181. )
  182. {
  183. if( FAILED ( _strUserMessage.Copy(*pstrUserMessage) ) )
  184. {
  185. return FALSE;
  186. }
  187. return TRUE;
  188. }
  189. BOOL
  190. IsExecDisabled(
  191. VOID
  192. )
  193. {
  194. if ( !_fIsLoadedSsiExecDisabled )
  195. {
  196. CHAR achSsiExecDisabled[ 2 ]; // to store "1" or "0"
  197. DWORD cchSsiExecDisabled = sizeof ( achSsiExecDisabled );
  198. //
  199. // We use lame way to retrieve SsiExecDisabled
  200. // There is internal variable that get's set
  201. // based on metabase setting
  202. //
  203. if ( !_pECB->GetServerVariable( _pECB->ConnID,
  204. "SSI_EXEC_DISABLED",
  205. achSsiExecDisabled,
  206. &cchSsiExecDisabled ) )
  207. {
  208. _fSsiExecDisabled = TRUE; // disable exec in the case of error
  209. }
  210. else
  211. {
  212. _fSsiExecDisabled =
  213. ( strcmp( achSsiExecDisabled, "1" ) == 0 ) ?
  214. TRUE : FALSE;
  215. }
  216. _fIsLoadedSsiExecDisabled = TRUE;
  217. }
  218. return _fSsiExecDisabled;
  219. }
  220. BOOL
  221. IsCmdDirectiveEnabled(
  222. VOID
  223. ) const
  224. {
  225. // Value is read from registry.
  226. // There is no metabase equivalent
  227. return sm_fEnableCmdDirective;
  228. }
  229. HRESULT
  230. SendCustomError(
  231. HSE_CUSTOM_ERROR_INFO * pCustomErrorInfo
  232. );
  233. HRESULT
  234. SendDate(
  235. IN SYSTEMTIME *,
  236. IN STRA *
  237. );
  238. HRESULT
  239. LookupVirtualRoot(
  240. IN WCHAR * pszVirtual,
  241. OUT STRU * pstrPhysical,
  242. IN DWORD dwAccess
  243. );
  244. HRESULT
  245. DoWork(
  246. IN HRESULT hr,
  247. OUT BOOL * pfAsyncPending
  248. );
  249. VOID
  250. AddToDelayedSIFDeleteList(
  251. SSI_INCLUDE_FILE * pSIF )
  252. /*++
  253. Routine Description:
  254. SSI_REQUEST will keep all the child SSI_INCLUDE_FILE
  255. instances on the list and delete them at the end of it's execution
  256. when all the response data was sent to client
  257. The reason for the delayed delete is that SSINC will try to buffer the
  258. response whenever possible to minimize number of response sends
  259. To send the response at the very end of the request processing
  260. all the child SSI_INCLUDE_FILE instances must be
  261. present at the time of sending the response
  262. Arguments:
  263. None
  264. Return Value:
  265. HRESULT
  266. --*/
  267. {
  268. InsertHeadList( &_DelayedSIFDeleteListHead,
  269. &pSIF->_DelayedDeleteListEntry );
  270. };
  271. static
  272. VOID WINAPI
  273. HseIoCompletion(
  274. IN EXTENSION_CONTROL_BLOCK * pECB,
  275. IN PVOID pContext,
  276. IN DWORD cbIO,
  277. IN DWORD dwError
  278. );
  279. private:
  280. //
  281. // private constructor
  282. // use CreateInstance to instantiate the object
  283. //
  284. SSI_REQUEST( EXTENSION_CONTROL_BLOCK * pECB );
  285. //
  286. // Not implemented methods
  287. // Declarations present to prevent compiler
  288. // to generate default ones.
  289. //
  290. SSI_REQUEST();
  291. SSI_REQUEST( const SSI_REQUEST& );
  292. SSI_REQUEST& operator=( const SSI_REQUEST& );
  293. HRESULT
  294. Initialize(
  295. VOID
  296. );
  297. EXTENSION_CONTROL_BLOCK * _pECB;
  298. // file name of the SSI (physical path)
  299. STRU _strFilename;
  300. // inline buffer for _strFilename
  301. WCHAR _achFilename[ SSI_DEFAULT_PATH_SIZE + 1 ];
  302. // URL of the SSI file requested
  303. STRU _strURL;
  304. // inline buffer for _strURL
  305. WCHAR _achURL[ SSI_DEFAULT_URL_SIZE + 1 ];
  306. // error message text configured by SSI file
  307. STRA _strUserMessage;
  308. // inline buffer for _struserMessage
  309. CHAR _achUserMessage[ SSI_DEFAULT_USER_MESSAGE + 1 ];
  310. // handle to the authenticated user
  311. HANDLE _hUser;
  312. // flag if Exec is disabled
  313. BOOL _fSsiExecDisabled;
  314. // flag if _fSsiExecDisabled was loaded already
  315. BOOL _fIsLoadedSsiExecDisabled;
  316. // Current include file (multiple stm files may be nested)
  317. SSI_INCLUDE_FILE * _pSIF;
  318. // Lookaside
  319. static ALLOC_CACHE_HANDLER * sm_pachSsiRequests;
  320. // is CMD execution enabled ?
  321. static BOOL sm_fEnableCmdDirective;
  322. // vector buffer - buffers data to be sent to client
  323. // to ensure bettter performance (sending too many very short
  324. // chunks of response data asynchronously is very ineficient
  325. SSI_VECTOR_BUFFER _VectorBuffer;
  326. // List of all SSI_INCLUDE_FILE instances that are needed
  327. // for the SSI_REQUEST processing
  328. LIST_ENTRY _DelayedSIFDeleteListHead;
  329. };
  330. #endif