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.

287 lines
8.5 KiB

  1. //+-------------------------------------------------------------------------
  2. //
  3. // Microsoft Windows
  4. //
  5. // Copyright (C) Microsoft Corporation, 1996 - 1999
  6. //
  7. // File: httptran.cxx
  8. //
  9. //--------------------------------------------------------------------------
  10. #include <windows.h>
  11. #include <tchar.h>
  12. #include <assert.h>
  13. #include <stdio.h>
  14. #include <stdlib.h>
  15. #include "GTTran.h"
  16. #include "IHGTTran.h"
  17. #include "httptran.hxx"
  18. DWORD __stdcall SendExp(HUTTRAN hTran, DWORD dwEncodeType, DWORD cbSendBuff, const BYTE * pbSendBuff) {
  19. return( ((CHttpTran *) hTran)->Send(dwEncodeType, cbSendBuff, pbSendBuff));
  20. }
  21. DWORD __stdcall ReceiveExp(HUTTRAN hTran, DWORD * pdwEncodeType, DWORD * pcbReceiveBuff, BYTE ** ppbReceiveBuff) {
  22. return( ((CHttpTran *) hTran)->Receive(pdwEncodeType, pcbReceiveBuff, ppbReceiveBuff));
  23. }
  24. DWORD __stdcall CloseExp(HUTTRAN hTran) {
  25. return(((CHttpTran *) hTran)->Close());
  26. }
  27. DWORD __stdcall FreeExp(HUTTRAN hTran, BYTE * pb) {
  28. return(((CHttpTran *) hTran)->Free(pb));
  29. }
  30. DWORD __stdcall OpenExp(HUTTRAN * phTran, const TCHAR * tszBinding, DWORD fOpen) {
  31. DWORD err;
  32. assert(phTran != NULL);
  33. if( (*phTran = (HUTTRAN) new CHttpTran(tszBinding)) == NULL )
  34. return(ERROR_NOT_ENOUGH_MEMORY);
  35. err = ((CHttpTran *) *phTran)->Open(tszBinding, fOpen);
  36. if(err != ERROR_SUCCESS)
  37. delete (CHttpTran *) (*phTran);
  38. return(err);
  39. }
  40. DWORD CHttpTran::Open(const TCHAR * tszURL, DWORD fOpenT) {
  41. TCHAR tszDomanName[_MAX_PATH];
  42. TCHAR tszPort[12];
  43. TCHAR * ptch;
  44. TCHAR * ptchT;
  45. DWORD err;
  46. // did we get a flag?
  47. if( (fOpenT & (GTREAD | GTWRITE)) == 0 )
  48. return(ERROR_INVALID_PARAMETER);
  49. // is it a readonly flag, then do gets
  50. fOpen = fOpenT;
  51. assert(tszURL != NULL);
  52. // we must have http://
  53. assert(_tcslen(tszURL) > 7);
  54. assert(_tcsnicmp(tszURL, TEXT("http://"), 7) == 0);
  55. // copy the Doman Name
  56. ptch = (TCHAR *) &tszURL[7];
  57. ptchT = tszDomanName;
  58. while(*ptch != _T('/') && *ptch != _T(':') && *ptch != 0)
  59. *ptchT++ = *ptch++;
  60. *ptchT = 0;
  61. // parse out the port number
  62. tszPort[0] = 0;
  63. if(*ptch == _T(':')) {
  64. ptchT = tszPort;
  65. while(*ptch != _T('/') && *ptch != 0)
  66. *ptchT++ = *ptch++;
  67. *ptchT = 0;
  68. }
  69. // Note, we don't support port numbers
  70. assert(tszPort[0] == 0);
  71. // save away what to look up.
  72. tszPartURL = new TCHAR[(_tcslen(ptch) + 1)];
  73. if (NULL == tszPartURL) {
  74. delete this;
  75. return(ERROR_NOT_ENOUGH_MEMORY);
  76. }
  77. _tcscpy(tszPartURL, ptch);
  78. // INTERNET_OPEN_TYPE_DIRECT,
  79. if( (hIOpen = InternetOpen( TEXT("Transport"),
  80. INTERNET_OPEN_TYPE_PRECONFIG,
  81. NULL,
  82. NULL,
  83. 0)) == NULL ||
  84. (hIConnect = InternetConnect(hIOpen,
  85. tszDomanName,
  86. INTERNET_INVALID_PORT_NUMBER,
  87. NULL,
  88. NULL,
  89. INTERNET_SERVICE_HTTP,
  90. 0,
  91. 0)) == NULL ) {
  92. err = GetLastError();
  93. delete this;
  94. return(err);
  95. }
  96. // If this is a GET, do a dummy send
  97. if( fOpen == GTREAD &&
  98. ((hIHttp = HttpOpenRequest(hIConnect,
  99. TEXT("GET"),
  100. tszPartURL,
  101. HTTP_VERSION,
  102. NULL,
  103. NULL,
  104. INTERNET_FLAG_DONT_CACHE,
  105. 0)) == NULL ||
  106. HttpSendRequest(hIHttp, TEXT("Accept: */*\r\n"), (DWORD) -1, NULL, 0) == FALSE) ) {
  107. err = GetLastError();
  108. delete this;
  109. return(err);
  110. }
  111. return(ERROR_SUCCESS);
  112. }
  113. DWORD CHttpTran::Send(DWORD dwEncodeType, DWORD cbSendBuff, const BYTE * pbSendBuff) {
  114. TCHAR tszBuff[1024];
  115. DWORD err;
  116. TCHAR * tszContentType;
  117. if( pbRecBuf != NULL || (fOpen & GTWRITE) != GTWRITE)
  118. return(ERROR_INVALID_PARAMETER);
  119. switch( dwEncodeType ) {
  120. case ASN_ENCODING:
  121. tszContentType = TEXT("application/x-octet-stream-asn");
  122. break;
  123. case TLV_ENCODING:
  124. tszContentType = TEXT("application/x-octet-stream-tlv");
  125. break;
  126. case IDL_ENCODING:
  127. tszContentType = TEXT("application/x-octet-stream-idl");
  128. break;
  129. case OCTET_ENCODING:
  130. tszContentType = TEXT("application/octet-stream");
  131. break;
  132. default:
  133. tszContentType = TEXT("text/*");
  134. break;
  135. }
  136. // say how long the buffer is
  137. _stprintf(tszBuff, TEXT("Content-Type: %s\r\nContent-Length: %d\r\nAccept: %s\r\n"), tszContentType, cbSendBuff,tszContentType);
  138. if( (hIHttp = HttpOpenRequest(hIConnect,
  139. TEXT("POST"),
  140. tszPartURL,
  141. HTTP_VERSION,
  142. NULL,
  143. NULL,
  144. INTERNET_FLAG_DONT_CACHE,
  145. 0)) == NULL ) {
  146. return(GetLastError());
  147. }
  148. // send of the request, this will wait for a response
  149. if( HttpSendRequest(hIHttp, tszBuff, (DWORD) -1, (LPVOID) pbSendBuff, cbSendBuff) == FALSE ) {
  150. err = GetLastError();
  151. // close out the handle
  152. assert(hIHttp != NULL);
  153. InternetCloseHandle(hIHttp);
  154. hIHttp = NULL;
  155. return(err);
  156. }
  157. return(ERROR_SUCCESS);
  158. }
  159. DWORD CHttpTran::Receive(DWORD * pdwEncodeType, DWORD * pcbReceiveBuff, BYTE ** ppbReceiveBuff) {
  160. TCHAR tszBuff[1024];
  161. DWORD cbBuff, cbBuffRead, cbBuffT;
  162. DWORD err;
  163. assert(pcbReceiveBuff != NULL && ppbReceiveBuff != NULL);
  164. *ppbReceiveBuff = NULL;
  165. *pcbReceiveBuff = 0;
  166. if( pbRecBuf != NULL || (fOpen & GTREAD) != GTREAD || hIHttp == NULL)
  167. return(ERROR_INVALID_PARAMETER);
  168. // get the content type
  169. if( pdwEncodeType != NULL) {
  170. cbBuff = sizeof(tszBuff);
  171. if(HttpQueryInfo( hIHttp,
  172. HTTP_QUERY_CONTENT_TYPE,
  173. tszBuff,
  174. &cbBuff,
  175. NULL) == FALSE)
  176. return(GetLastError());
  177. assert(cbBuff > 0);
  178. if(!_tcscmp(TEXT("application/x-octet-stream-asn"), tszBuff))
  179. *pdwEncodeType = ASN_ENCODING;
  180. else if(!_tcscmp(TEXT("application/x-octet-stream-idl"), tszBuff))
  181. *pdwEncodeType = IDL_ENCODING;
  182. else if(!_tcscmp(TEXT("application/x-octet-stream-tlv"), tszBuff))
  183. *pdwEncodeType = TLV_ENCODING;
  184. else if(!_tcscmp(TEXT("application/octet-stream"), tszBuff))
  185. *pdwEncodeType = OCTET_ENCODING;
  186. else
  187. *pdwEncodeType = ASCII_ENCODING;
  188. }
  189. // now get the length of the buffer returned
  190. cbBuff = sizeof(tszBuff);
  191. if(HttpQueryInfo( hIHttp,
  192. HTTP_QUERY_CONTENT_LENGTH,
  193. tszBuff,
  194. &cbBuff,
  195. NULL) == FALSE)
  196. return(GetLastError());
  197. assert(cbBuff > 0);
  198. cbBuff = _ttol(tszBuff);
  199. // allocate a buffer
  200. if( (pbRecBuf = new BYTE[cbBuff]) == NULL )
  201. return(ERROR_NOT_ENOUGH_MEMORY);
  202. // read the data
  203. cbBuffRead = 0;
  204. while(cbBuffRead < cbBuff) {
  205. cbBuffT = 0;
  206. if(InternetReadFile(hIHttp, &pbRecBuf[cbBuffRead], (cbBuff - cbBuffRead), &cbBuffT) == FALSE ) {
  207. err = GetLastError();
  208. delete [] pbRecBuf;
  209. pbRecBuf = NULL;
  210. return(err);
  211. }
  212. cbBuffRead += cbBuffT;
  213. }
  214. // close out the handle
  215. InternetCloseHandle(hIHttp);
  216. hIHttp = NULL;
  217. // pass back the info
  218. *ppbReceiveBuff = pbRecBuf;
  219. *pcbReceiveBuff = cbBuff;
  220. return(ERROR_SUCCESS);
  221. }
  222. DWORD CHttpTran::Free(BYTE * pb) {
  223. assert(pb == pbRecBuf);
  224. delete [] pbRecBuf;
  225. pbRecBuf = NULL;
  226. return(ERROR_SUCCESS);
  227. }
  228. DWORD CHttpTran::Close(void) {
  229. delete this;
  230. return(ERROR_SUCCESS);
  231. }