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.

513 lines
13 KiB

  1. /*
  2. (C) Copyright 1998
  3. All rights reserved.
  4. Portions of this software are:
  5. (C) Copyright 1995, 1999 TriplePoint, Inc. -- http://www.TriplePoint.com
  6. License to use this software is granted under the terms outlined in
  7. the TriplePoint Software Services Agreement.
  8. (C) Copyright 1992 Microsoft Corp. -- http://www.Microsoft.com
  9. License to use this software is granted under the terms outlined in
  10. the Microsoft Windows Device Driver Development Kit.
  11. @doc INTERNAL Port Port_c
  12. @module Port.c |
  13. This module implements the interface to the <t PORT_OBJECT>.
  14. @head3 Contents |
  15. @index class,mfunc,func,msg,mdata,struct,enum | Port_c
  16. @end
  17. */
  18. #define __FILEID__ PORT_OBJECT_TYPE
  19. // Unique file ID for error logging
  20. #include "Miniport.h" // Defines all the miniport objects
  21. #if defined(NDIS_LCODE)
  22. # pragma NDIS_LCODE // Windows 95 wants this code locked down!
  23. # pragma NDIS_LDATA
  24. #endif
  25. DBG_STATIC ULONG g_PortInstanceCounter = 0;
  26. // Keeps track of how many <t PORT_OBJECT>s are created.
  27. /* @doc EXTERNAL INTERNAL Port Port_c g_PortParameters
  28. @topic 5.6 Port Parameters |
  29. This section describes the registry parameters read into the
  30. <t PORT_OBJECT>.
  31. @globalv PARAM_TABLE | g_PortParameters |
  32. This table defines the registry based parameters to be assigned to data
  33. members of the <t PORT_OBJECT>.
  34. <f Note>:
  35. If you add any registry based data members to <t PORT_OBJECT>
  36. you will need to modify <f PortReadParameters> and add the parameter
  37. definitions to the <f g_PortParameters> table.
  38. */
  39. DBG_STATIC PARAM_TABLE g_PortParameters[] =
  40. {
  41. PARAM_ENTRY(PORT_OBJECT,
  42. SwitchType, PARAM_SwitchType,
  43. FALSE, NdisParameterInteger, 0,
  44. 0x0001, 0x0001, 0x8000),
  45. PARAM_ENTRY(PORT_OBJECT,
  46. NumChannels, PARAM_NumBChannels,
  47. FALSE, NdisParameterInteger, 0,
  48. 2, 2, 24),
  49. /* The last entry must be an empty string! */
  50. { { 0 } }
  51. };
  52. DBG_STATIC NDIS_STRING PortPrefix = INIT_STRING_CONST(PARAM_PORT_PREFIX);
  53. /* @doc INTERNAL Port Port_c PortReadParameters
  54. @func
  55. <f PortReadParameters> reads the Port parameters from the registry
  56. and initializes the associated data members. This should only be called
  57. by <f PortCreate>.
  58. <f Note>:
  59. If you add any registry based data members to <t PORT_OBJECT>
  60. you will need to modify <f PortReadParameters> and add the parameter
  61. definitions to the <f g_PortParameters> table.
  62. @rdesc
  63. <f PortReadParameters> returns zero if it is successful.<nl>
  64. Otherwise, a non-zero return value indicates an error condition.
  65. */
  66. DBG_STATIC NDIS_STATUS PortReadParameters(
  67. IN PPORT_OBJECT pPort // @parm
  68. // A pointer to the <t PORT_OBJECT> returned by <f PortCreate>.
  69. )
  70. {
  71. DBG_FUNC("PortReadParameters")
  72. NDIS_STATUS Status;
  73. // Status result returned from an NDIS function call.
  74. PMINIPORT_ADAPTER_OBJECT pAdapter;
  75. // A pointer to the <t MINIPORT_ADAPTER_OBJECT>.
  76. ASSERT(pPort && pPort->ObjectType == PORT_OBJECT_TYPE);
  77. pAdapter = GET_ADAPTER_FROM_PORT(pPort);
  78. DBG_ENTER(pAdapter);
  79. /*
  80. // Parse the registry parameters.
  81. */
  82. Status = ParamParseRegistry(
  83. pAdapter->MiniportAdapterHandle,
  84. pAdapter->WrapperConfigurationContext,
  85. (PUCHAR)pPort,
  86. g_PortParameters
  87. );
  88. DBG_NOTICE(pAdapter,("PortPrefixLen=%d:%d:%ls\n",
  89. PortPrefix.Length, PortPrefix.MaximumLength, PortPrefix.Buffer));
  90. if (Status == NDIS_STATUS_SUCCESS)
  91. {
  92. /*
  93. // Make sure the parameters are valid.
  94. */
  95. if (pPort->TODO)
  96. {
  97. DBG_ERROR(pAdapter,("Invalid parameter\n"
  98. ));
  99. NdisWriteErrorLogEntry(
  100. pAdapter->MiniportAdapterHandle,
  101. NDIS_ERROR_CODE_UNSUPPORTED_CONFIGURATION,
  102. 3,
  103. pPort->TODO,
  104. __FILEID__,
  105. __LINE__
  106. );
  107. Status = NDIS_STATUS_FAILURE;
  108. }
  109. else
  110. {
  111. /*
  112. // Finish setting up data members based on registry settings.
  113. */
  114. }
  115. }
  116. DBG_RETURN(pAdapter, Status);
  117. return (Status);
  118. }
  119. /* @doc INTERNAL Port Port_c PortCreateObjects
  120. @func
  121. <f PortCreateObjects> calls the create routines for all the objects
  122. contained in <t PORT_OBJECT>. This should only be called
  123. by <f PortCreate>.
  124. <f Note>:
  125. If you add any new objects to <t PORT_OBJECT> you will need
  126. to modify <f PortCreateObjects> and <f PortDestroyObjects> so they
  127. will get created and destroyed properly.
  128. @rdesc
  129. <f PortCreateObjects> returns zero if it is successful.<nl>
  130. Otherwise, a non-zero return value indicates an error condition.
  131. */
  132. DBG_STATIC NDIS_STATUS PortCreateObjects(
  133. IN PPORT_OBJECT pPort // @parm
  134. // A pointer to the <t PORT_OBJECT> returned by <f PortCreate>.
  135. )
  136. {
  137. DBG_FUNC("PortCreateObjects")
  138. NDIS_STATUS Result = NDIS_STATUS_SUCCESS;
  139. // Holds the result code returned by this function.
  140. PMINIPORT_ADAPTER_OBJECT pAdapter;
  141. // A pointer to the <t MINIPORT_ADAPTER_OBJECT>.
  142. ASSERT(pPort && pPort->ObjectType == PORT_OBJECT_TYPE);
  143. pAdapter = GET_ADAPTER_FROM_PORT(pPort);
  144. DBG_ENTER(pAdapter);
  145. // TODO - Add code here
  146. DBG_RETURN(pAdapter, Result);
  147. return (Result);
  148. }
  149. /* @doc INTERNAL Port Port_c PortCreate
  150. @func
  151. <f PortCreate> allocates memory for a <t PORT_OBJECT> and then
  152. initializes the data members to their starting state.
  153. If successful, <p ppPort> will be set to point to the newly created
  154. <t PORT_OBJECT>. Otherwise, <p ppPort> will be set to NULL.
  155. @comm
  156. This function should be called only once when the Miniport is loaded.
  157. Before the Miniport is unloaded, <f PortDestroy> must be called to
  158. release the <t PORT_OBJECT> created by this function.
  159. @rdesc
  160. <f PortCreate> returns zero if it is successful.<nl>
  161. Otherwise, a non-zero return value indicates an error condition.
  162. */
  163. NDIS_STATUS PortCreate(
  164. OUT PPORT_OBJECT * ppPort, // @parm
  165. // Points to a caller-defined memory location to which this function
  166. // writes the virtual address of the allocated <t PORT_OBJECT>.
  167. IN PCARD_OBJECT pCard // @parm
  168. // A pointer to the <t CARD_OBJECT> returned by <f CardCreate>.
  169. )
  170. {
  171. DBG_FUNC("PortCreate")
  172. PPORT_OBJECT pPort;
  173. // Pointer to our newly allocated object.
  174. NDIS_STATUS Result = NDIS_STATUS_SUCCESS;
  175. // Holds the result code returned by this function.
  176. PMINIPORT_ADAPTER_OBJECT pAdapter;
  177. // A pointer to the <t MINIPORT_ADAPTER_OBJECT>.
  178. ASSERT(pCard && pCard->ObjectType == CARD_OBJECT_TYPE);
  179. pAdapter = GET_ADAPTER_FROM_CARD(pCard);
  180. DBG_ENTER(pAdapter);
  181. /*
  182. // Make sure the caller's object pointer is NULL to begin with.
  183. // It will be set later only if everything is successful.
  184. */
  185. *ppPort = NULL;
  186. /*
  187. // Allocate memory for the object.
  188. */
  189. Result = ALLOCATE_OBJECT(pPort, pAdapter->MiniportAdapterHandle);
  190. if (Result == NDIS_STATUS_SUCCESS)
  191. {
  192. /*
  193. // Zero everything to begin with.
  194. // Then set the object type and assign a unique ID .
  195. */
  196. pPort->ObjectType = PORT_OBJECT_TYPE;
  197. pPort->ObjectID = ++g_PortInstanceCounter;
  198. /*
  199. // Initialize the member variables to their default settings.
  200. */
  201. pPort->pCard = pCard;
  202. // TODO - Add code here
  203. /*
  204. // Parse the registry parameters.
  205. */
  206. Result = PortReadParameters(pPort);
  207. /*
  208. // If all goes well, we are ready to create the sub-components.
  209. */
  210. if (Result == NDIS_STATUS_SUCCESS)
  211. {
  212. Result = PortCreateObjects(pPort);
  213. }
  214. if (Result == NDIS_STATUS_SUCCESS)
  215. {
  216. /*
  217. // All is well, so return the object pointer to the caller.
  218. */
  219. *ppPort = pPort;
  220. }
  221. else
  222. {
  223. /*
  224. // Something went wrong, so let's make sure everything is
  225. // cleaned up.
  226. */
  227. PortDestroy(pPort);
  228. }
  229. }
  230. DBG_RETURN(pAdapter, Result);
  231. return (Result);
  232. }
  233. /* @doc INTERNAL Port Port_c PortDestroyObjects
  234. @func
  235. <f PortDestroyObjects> calls the destroy routines for all the objects
  236. contained in <t PORT_OBJECT>. This should only be called by
  237. <f PortDestroy>.
  238. <f Note>:
  239. If you add any new objects to <t PPORT_OBJECT> you will need to
  240. modify <f PortCreateObjects> and <f PortDestroyObjects> so they
  241. will get created and destroyed properly.
  242. */
  243. DBG_STATIC void PortDestroyObjects(
  244. IN PPORT_OBJECT pPort // @parm
  245. // A pointer to the <t PORT_OBJECT> instance.
  246. )
  247. {
  248. DBG_FUNC("PortDestroyObjects")
  249. PMINIPORT_ADAPTER_OBJECT pAdapter;
  250. // A pointer to the <t MINIPORT_ADAPTER_OBJECT>.
  251. ASSERT(pPort && pPort->ObjectType == PORT_OBJECT_TYPE);
  252. pAdapter = GET_ADAPTER_FROM_PORT(pPort);
  253. DBG_ENTER(pAdapter);
  254. // TODO - Add code here
  255. DBG_LEAVE(pAdapter);
  256. }
  257. /* @doc INTERNAL Port Port_c PortDestroy
  258. @func
  259. <f PortDestroy> frees the memory for this <t PORT_OBJECT>.
  260. All memory allocated by <f PortCreate> will be released back to the
  261. OS.
  262. */
  263. void PortDestroy(
  264. IN PPORT_OBJECT pPort // @parm
  265. // A pointer to the <t PORT_OBJECT> returned by <f PortCreate>.
  266. )
  267. {
  268. DBG_FUNC("PortDestroy")
  269. PMINIPORT_ADAPTER_OBJECT pAdapter;
  270. // A pointer to the <t MINIPORT_ADAPTER_OBJECT>.
  271. if (pPort)
  272. {
  273. ASSERT(pPort->ObjectType == PORT_OBJECT_TYPE);
  274. pAdapter = GET_ADAPTER_FROM_PORT(pPort);
  275. DBG_ENTER(pAdapter);
  276. // TODO - Add code here
  277. /*
  278. // Release all objects allocated within this object.
  279. */
  280. PortDestroyObjects(pPort);
  281. /*
  282. // Make sure we fail the ASSERT if we see this object again.
  283. */
  284. pPort->ObjectType = 0;
  285. FREE_OBJECT(pPort);
  286. DBG_LEAVE(pAdapter);
  287. }
  288. }
  289. /* @doc INTERNAL Port Port_c PortOpen
  290. @func
  291. <f PortOpen> makes the Port connection ready to transmit and
  292. receive data.
  293. @rdesc
  294. <f PortOpen> returns zero if it is successful.<nl>
  295. Otherwise, a non-zero return value indicates an error condition.
  296. */
  297. NDIS_STATUS PortOpen(
  298. IN PPORT_OBJECT pPort, // @parm
  299. // A pointer to the <t PORT_OBJECT> associated with this request.
  300. IN PBCHANNEL_OBJECT pBChannel // @parm
  301. // A pointer to the <t BCHANNEL_OBJECT> to be associated with this
  302. // Port.
  303. )
  304. {
  305. DBG_FUNC("PortOpen")
  306. NDIS_STATUS Result = NDIS_STATUS_SUCCESS;
  307. // Holds the result code returned by this function.
  308. PMINIPORT_ADAPTER_OBJECT pAdapter;
  309. // A pointer to the <t MINIPORT_ADAPTER_OBJECT>.
  310. ASSERT(pBChannel);
  311. ASSERT(pPort && pPort->ObjectType == PORT_OBJECT_TYPE);
  312. pAdapter = GET_ADAPTER_FROM_PORT(pPort);
  313. DBG_ENTER(pAdapter);
  314. if (!pPort->IsOpen)
  315. {
  316. DBG_NOTICE(pAdapter,("Opening Port #%d\n",
  317. pPort->ObjectID));
  318. // TODO - Add code here
  319. pPort->IsOpen = TRUE;
  320. }
  321. else
  322. {
  323. DBG_ERROR(pAdapter,("Port #%d already opened\n",
  324. pPort->ObjectID));
  325. }
  326. DBG_RETURN(pAdapter, Result);
  327. return (Result);
  328. }
  329. /* @doc INTERNAL Port Port_c PortClose
  330. @func
  331. <f PortClose> closes the given B-channel.
  332. */
  333. void PortClose(
  334. IN PPORT_OBJECT pPort // @parm
  335. // A pointer to the <t PORT_OBJECT> associated with this request.
  336. )
  337. {
  338. DBG_FUNC("PortClose")
  339. PMINIPORT_ADAPTER_OBJECT pAdapter;
  340. // A pointer to the <t MINIPORT_ADAPTER_OBJECT>.
  341. ASSERT(pPort && pPort->ObjectType == PORT_OBJECT_TYPE);
  342. pAdapter = GET_ADAPTER_FROM_PORT(pPort);
  343. DBG_ENTER(pAdapter);
  344. if (pPort->IsOpen)
  345. {
  346. DBG_NOTICE(pAdapter,("Closing Port #%d\n",
  347. pPort->ObjectID));
  348. // TODO - Add code here
  349. pPort->IsOpen = FALSE;
  350. }
  351. else
  352. {
  353. DBG_ERROR(pAdapter,("Port #%d already closed\n",
  354. pPort->ObjectID));
  355. }
  356. DBG_LEAVE(pAdapter);
  357. }