Source code of Windows XP (NT5)
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.

579 lines
11 KiB

  1. /*++
  2. Copyright (c) 1997 Microsoft Corporation
  3. Module Name:
  4. faxroute.cpp
  5. Abstract:
  6. This file implements the CFaxRoutingMethod and
  7. CFaxRoutingMethods interfaces.
  8. Author:
  9. Wesley Witt (wesw) 1-June-1997
  10. Environment:
  11. User Mode
  12. --*/
  13. #include "stdafx.h"
  14. #include "faxroute.h"
  15. CFaxRoutingMethod::CFaxRoutingMethod()
  16. {
  17. m_pFaxPort = NULL;
  18. m_LastFaxError = NO_ERROR;
  19. m_DeviceId = 0;
  20. m_Enabled = FALSE;
  21. m_DeviceName = NULL;
  22. m_Guid = NULL;
  23. m_FunctionName = NULL;
  24. m_ImageName = NULL;
  25. m_FriendlyName = NULL;
  26. }
  27. CFaxRoutingMethod::~CFaxRoutingMethod()
  28. {
  29. if (m_pFaxPort) {
  30. m_pFaxPort->Release();
  31. }
  32. if (m_DeviceName) {
  33. SysFreeString( m_DeviceName );
  34. }
  35. if (m_Guid) {
  36. SysFreeString( m_Guid );
  37. }
  38. if (m_FunctionName) {
  39. SysFreeString( m_FunctionName );
  40. }
  41. if (m_ImageName) {
  42. SysFreeString( m_ImageName );
  43. }
  44. if (m_FriendlyName) {
  45. SysFreeString( m_FriendlyName );
  46. }
  47. if (m_ExtensionName) {
  48. SysFreeString( m_ExtensionName );
  49. }
  50. if (m_RoutingData) {
  51. FaxFreeBuffer( m_RoutingData );
  52. }
  53. }
  54. BOOL
  55. CFaxRoutingMethod::Initialize(
  56. CFaxPort *i_pFaxPort,
  57. DWORD i_DeviceId,
  58. BOOL i_Enabled,
  59. LPCWSTR i_DeviceName,
  60. LPCWSTR i_Guid,
  61. LPCWSTR i_FunctionName,
  62. LPCWSTR i_FriendlyName,
  63. LPCWSTR i_ImageName,
  64. LPCWSTR i_ExtensionName
  65. )
  66. {
  67. HRESULT hr;
  68. m_pFaxPort = i_pFaxPort;
  69. m_DeviceId = i_DeviceId;
  70. m_Enabled = i_Enabled;
  71. m_DeviceName = SysAllocString(i_DeviceName);
  72. m_Guid = SysAllocString(i_Guid);
  73. m_FunctionName = SysAllocString(i_FunctionName);
  74. m_ImageName = SysAllocString(i_ImageName);
  75. m_FriendlyName = SysAllocString(i_FriendlyName);
  76. m_ExtensionName = SysAllocString(i_ExtensionName);
  77. m_RoutingData = NULL;
  78. if ( (!m_DeviceName && i_DeviceName) ||
  79. (!m_Guid && i_Guid) ||
  80. (!m_FunctionName && i_FunctionName) ||
  81. (!m_ImageName && i_ImageName) ||
  82. (!m_FriendlyName && i_FriendlyName) ||
  83. (!m_ExtensionName && i_ExtensionName)
  84. ) {
  85. SysFreeString(m_DeviceName);
  86. SysFreeString(m_Guid);
  87. SysFreeString(m_FunctionName);
  88. SysFreeString(m_ImageName);
  89. SysFreeString(m_FriendlyName);
  90. SysFreeString(m_ExtensionName);
  91. return FALSE;
  92. }
  93. if (!m_pFaxPort) {
  94. return FALSE;
  95. }
  96. hr = m_pFaxPort->AddRef();
  97. if (FAILED(hr)) {
  98. m_pFaxPort = NULL;
  99. return FALSE;
  100. }
  101. DWORD Size = 0;
  102. if (!FaxGetRoutingInfoW( m_pFaxPort->GetPortHandle(), m_Guid, &m_RoutingData, &Size )) {
  103. m_RoutingData = NULL;
  104. m_LastFaxError = GetLastError();
  105. return FALSE;
  106. }
  107. if (Size == 0) {
  108. FaxFreeBuffer( m_RoutingData );
  109. m_RoutingData = NULL;
  110. }
  111. return TRUE;
  112. }
  113. STDMETHODIMP CFaxRoutingMethod::InterfaceSupportsErrorInfo(REFIID riid)
  114. {
  115. static const IID* arr[] = { &IID_IFaxRoutingMethod };
  116. for (int i=0;i<sizeof(arr)/sizeof(arr[0]);i++) {
  117. if (InlineIsEqualGUID(*arr[i],riid)) {
  118. return S_OK;
  119. }
  120. }
  121. return S_FALSE;
  122. }
  123. STDMETHODIMP CFaxRoutingMethod::get_DeviceId(long * pVal)
  124. {
  125. if (!pVal) {
  126. return E_POINTER;
  127. }
  128. __try {
  129. *pVal = m_DeviceId;
  130. return S_OK;
  131. } __except (EXCEPTION_EXECUTE_HANDLER) {
  132. }
  133. return E_UNEXPECTED;
  134. }
  135. STDMETHODIMP CFaxRoutingMethod::get_Enable(BOOL * pVal)
  136. {
  137. if (!pVal) {
  138. return E_POINTER;
  139. }
  140. __try {
  141. *pVal = m_Enabled;
  142. return S_OK;
  143. } __except (EXCEPTION_EXECUTE_HANDLER) {
  144. }
  145. return E_UNEXPECTED;
  146. }
  147. STDMETHODIMP CFaxRoutingMethod::put_Enable(BOOL newVal)
  148. {
  149. if (!FaxEnableRoutingMethodW( m_pFaxPort->GetPortHandle(), m_Guid, newVal)) {
  150. return HRESULT_FROM_WIN32(GetLastError());
  151. }
  152. m_Enabled = newVal;
  153. return S_OK;
  154. }
  155. STDMETHODIMP CFaxRoutingMethod::get_DeviceName(BSTR * pVal)
  156. {
  157. if (!pVal) {
  158. return E_POINTER;
  159. }
  160. BSTR Copy = SysAllocString(m_DeviceName);
  161. if (!Copy && m_DeviceName) {
  162. return E_OUTOFMEMORY;
  163. }
  164. __try {
  165. *pVal = Copy;
  166. return S_OK;
  167. } __except (EXCEPTION_EXECUTE_HANDLER) {
  168. SysFreeString(Copy);
  169. }
  170. return E_UNEXPECTED;
  171. }
  172. STDMETHODIMP CFaxRoutingMethod::get_Guid(BSTR * pVal)
  173. {
  174. if (!pVal) {
  175. return E_POINTER;
  176. }
  177. BSTR Copy = SysAllocString(m_Guid);
  178. if (!Copy && m_Guid) {
  179. return E_OUTOFMEMORY;
  180. }
  181. __try {
  182. *pVal = Copy;
  183. return S_OK;
  184. } __except (EXCEPTION_EXECUTE_HANDLER) {
  185. SysFreeString(Copy);
  186. }
  187. return E_UNEXPECTED;
  188. }
  189. STDMETHODIMP CFaxRoutingMethod::get_FunctionName(BSTR * pVal)
  190. {
  191. if (!pVal) {
  192. return E_POINTER;
  193. }
  194. BSTR Copy = SysAllocString(m_FunctionName);
  195. if (!Copy && m_FunctionName) {
  196. return E_OUTOFMEMORY;
  197. }
  198. __try {
  199. *pVal = Copy;
  200. return S_OK;
  201. } __except (EXCEPTION_EXECUTE_HANDLER) {
  202. SysFreeString(Copy);
  203. }
  204. return E_UNEXPECTED;
  205. }
  206. STDMETHODIMP CFaxRoutingMethod::get_ImageName(BSTR * pVal)
  207. {
  208. if (!pVal) {
  209. return E_POINTER;
  210. }
  211. BSTR Copy = SysAllocString(m_ImageName);
  212. if (!Copy && m_ImageName) {
  213. return E_OUTOFMEMORY;
  214. }
  215. __try {
  216. *pVal = Copy;
  217. return S_OK;
  218. } __except (EXCEPTION_EXECUTE_HANDLER) {
  219. SysFreeString(Copy);
  220. }
  221. return E_UNEXPECTED;
  222. }
  223. STDMETHODIMP CFaxRoutingMethod::get_FriendlyName(BSTR * pVal)
  224. {
  225. if (!pVal) {
  226. return E_POINTER;
  227. }
  228. BSTR Copy = SysAllocString(m_FriendlyName);
  229. if (!Copy && m_FriendlyName) {
  230. return E_OUTOFMEMORY;
  231. }
  232. __try {
  233. *pVal = Copy;
  234. return S_OK;
  235. } __except (EXCEPTION_EXECUTE_HANDLER) {
  236. SysFreeString(Copy);
  237. }
  238. return E_UNEXPECTED;
  239. }
  240. STDMETHODIMP CFaxRoutingMethod::get_ExtensionName(BSTR * pVal)
  241. {
  242. if (!pVal) {
  243. return E_POINTER;
  244. }
  245. BSTR Copy = SysAllocString(m_ExtensionName);
  246. if (!Copy && m_ExtensionName) {
  247. return E_OUTOFMEMORY;
  248. }
  249. __try {
  250. *pVal = Copy;
  251. return S_OK;
  252. } __except (EXCEPTION_EXECUTE_HANDLER) {
  253. SysFreeString(Copy);
  254. }
  255. return E_UNEXPECTED;
  256. }
  257. STDMETHODIMP CFaxRoutingMethod::get_RoutingData(BSTR * pVal)
  258. {
  259. if (!pVal) {
  260. return E_POINTER;
  261. }
  262. BSTR Copy;
  263. Copy = NULL;
  264. __try {
  265. if (m_RoutingData == NULL) {
  266. Copy = SysAllocString( L"" );
  267. } else if (*((LPDWORD)m_RoutingData) == 0 || *((LPDWORD)m_RoutingData) == 1) {
  268. Copy = SysAllocString( (LPWSTR)(m_RoutingData + sizeof(DWORD)) );
  269. if (!Copy && (LPWSTR)(m_RoutingData + sizeof(DWORD))) {
  270. return E_OUTOFMEMORY;
  271. }
  272. } else {
  273. return E_UNEXPECTED;
  274. }
  275. if (!Copy) {
  276. return E_OUTOFMEMORY;
  277. }
  278. *pVal = Copy;
  279. return S_OK;
  280. } __except (EXCEPTION_EXECUTE_HANDLER) {
  281. if (Copy != NULL) {
  282. SysFreeString(Copy);
  283. }
  284. }
  285. return E_UNEXPECTED;
  286. }
  287. CFaxRoutingMethods::CFaxRoutingMethods()
  288. {
  289. m_pFaxPort = NULL;
  290. m_LastFaxError = 0;
  291. m_MethodCount = 0;
  292. m_VarVect = NULL;
  293. }
  294. CFaxRoutingMethods::~CFaxRoutingMethods()
  295. {
  296. if (m_pFaxPort) {
  297. m_pFaxPort->Release();
  298. }
  299. if (m_VarVect) {
  300. delete [] m_VarVect;
  301. }
  302. }
  303. BOOL CFaxRoutingMethods::Init(CFaxPort *pFaxPort)
  304. {
  305. HRESULT hr;
  306. if (!pFaxPort) {
  307. return FALSE;
  308. }
  309. m_pFaxPort = pFaxPort;
  310. hr = m_pFaxPort->AddRef();
  311. if (FAILED(hr)) {
  312. m_pFaxPort = NULL;
  313. return FALSE;
  314. }
  315. PFAX_ROUTING_METHODW RoutingMethod = NULL;
  316. DWORD Size = 0;
  317. //
  318. // get the routing methods from the server
  319. //
  320. if (!FaxEnumRoutingMethodsW( m_pFaxPort->GetPortHandle(), &RoutingMethod, &m_MethodCount )) {
  321. m_LastFaxError = GetLastError();
  322. return FALSE;
  323. }
  324. //
  325. // enumerate the methods
  326. //
  327. m_VarVect = new CComVariant[m_MethodCount];
  328. if (!m_VarVect) {
  329. FaxFreeBuffer( RoutingMethod );
  330. return FALSE;
  331. }
  332. for (DWORD i=0; i<m_MethodCount; i++) {
  333. //
  334. // create the object
  335. //
  336. CComObject<CFaxRoutingMethod> *pFaxRoutingMethod;
  337. HRESULT hr = CComObject<CFaxRoutingMethod>::CreateInstance( &pFaxRoutingMethod );
  338. if (FAILED(hr)) {
  339. delete [] m_VarVect;
  340. m_VarVect = NULL;
  341. FaxFreeBuffer( RoutingMethod );
  342. return FALSE;
  343. }
  344. //
  345. // set the values
  346. //
  347. if (!pFaxRoutingMethod->Initialize(
  348. m_pFaxPort,
  349. RoutingMethod[i].DeviceId,
  350. RoutingMethod[i].Enabled,
  351. RoutingMethod[i].DeviceName,
  352. RoutingMethod[i].Guid,
  353. RoutingMethod[i].FunctionName,
  354. RoutingMethod[i].FriendlyName,
  355. RoutingMethod[i].ExtensionImageName,
  356. RoutingMethod[i].ExtensionFriendlyName
  357. ))
  358. {
  359. delete [] m_VarVect;
  360. m_VarVect = NULL;
  361. FaxFreeBuffer( RoutingMethod );
  362. return FALSE;
  363. }
  364. //
  365. // get IDispatch pointer
  366. //
  367. LPDISPATCH lpDisp = NULL;
  368. hr = pFaxRoutingMethod->QueryInterface( IID_IDispatch, (void**)&lpDisp );
  369. if (FAILED(hr)) {
  370. delete [] m_VarVect;
  371. m_VarVect = NULL;
  372. FaxFreeBuffer( RoutingMethod );
  373. return FALSE;
  374. }
  375. //
  376. // create a variant and add it to the collection
  377. //
  378. CComVariant &var = m_VarVect[i];
  379. __try {
  380. var.vt = VT_DISPATCH;
  381. var.pdispVal = lpDisp;
  382. hr = S_OK;
  383. } __except (EXCEPTION_EXECUTE_HANDLER) {
  384. hr = E_UNEXPECTED;
  385. }
  386. if (FAILED(hr)) {
  387. delete [] m_VarVect;
  388. m_VarVect = NULL;
  389. FaxFreeBuffer( RoutingMethod );
  390. return FALSE;
  391. }
  392. }
  393. FaxFreeBuffer( RoutingMethod );
  394. return TRUE;
  395. }
  396. STDMETHODIMP CFaxRoutingMethods::get_Item(long Index, VARIANT * retval)
  397. {
  398. if (!retval) {
  399. return E_POINTER;
  400. }
  401. //
  402. // use 1-based index, VB like
  403. //
  404. if ((Index < 1) || (Index > (long) m_MethodCount)) {
  405. return E_INVALIDARG;
  406. }
  407. __try {
  408. VariantInit( retval );
  409. retval->vt = VT_UNKNOWN;
  410. retval->punkVal = NULL;
  411. return VariantCopy( retval, &m_VarVect[Index-1] );
  412. } __except (EXCEPTION_EXECUTE_HANDLER) {
  413. }
  414. return E_UNEXPECTED;
  415. }
  416. STDMETHODIMP CFaxRoutingMethods::get_Count(long * pVal)
  417. {
  418. if (!pVal) {
  419. return E_POINTER;
  420. }
  421. __try {
  422. *pVal = m_MethodCount;
  423. return S_OK;
  424. } __except (EXCEPTION_EXECUTE_HANDLER) {
  425. }
  426. return E_UNEXPECTED;
  427. }