1 /*******************************************************************************
2 *Copyright (c) 2014 PMC-Sierra, Inc. All rights reserved.
3 *
4 *Redistribution and use in source and binary forms, with or without modification, are permitted provided
5 *that the following conditions are met:
6 *1. Redistributions of source code must retain the above copyright notice, this list of conditions and the
7 *following disclaimer.
8 *2. Redistributions in binary form must reproduce the above copyright notice,
9 *this list of conditions and the following disclaimer in the documentation and/or other materials provided
10 *with the distribution.
11 *
12 *THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND ANY EXPRESS OR IMPLIED
13 *WARRANTIES,INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
14 *FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
15 *FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
16 *NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
17 *BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
18 *LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
19 *SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE
20
21 ********************************************************************************/
22 #include <sys/cdefs.h>
23 #include <dev/pms/config.h>
24
25 #include <dev/pms/freebsd/driver/common/osenv.h>
26 #include <dev/pms/freebsd/driver/common/ostypes.h>
27 #include <dev/pms/freebsd/driver/common/osdebug.h>
28
29 #include <dev/pms/RefTisa/sallsdk/api/sa.h>
30 #include <dev/pms/RefTisa/sallsdk/api/saapi.h>
31 #include <dev/pms/RefTisa/sallsdk/api/saosapi.h>
32
33 #ifdef FDS_DM
34 #include <dev/pms/RefTisa/discovery/api/dm.h>
35 #include <dev/pms/RefTisa/discovery/api/dmapi.h>
36 #include <dev/pms/RefTisa/discovery/api/tddmapi.h>
37
38 #include <dev/pms/RefTisa/discovery/dm/dmdefs.h>
39 #include <dev/pms/RefTisa/discovery/dm/dmtypes.h>
40 #include <dev/pms/RefTisa/discovery/dm/dmproto.h>
41
42 /*****************************************************************************/
43 /*! \brief dmCreatePort
44 *
45 *
46 * Purpose: A port context is created by this function
47 *
48 * \param dmRoot: DM context handle.
49 * \param dmPortContext: Pointer to this instance of port context
50 *
51 * \return:
52 * DM_RC_SUCCESS
53 * DM_RC_FAILURE
54 *
55 */
56 /*****************************************************************************/
57 osGLOBAL bit32
dmCreatePort(dmRoot_t * dmRoot,dmPortContext_t * dmPortContext,dmPortInfo_t * dmPortInfo)58 dmCreatePort(
59 dmRoot_t *dmRoot,
60 dmPortContext_t *dmPortContext,
61 dmPortInfo_t *dmPortInfo)
62 {
63 dmIntRoot_t *dmIntRoot = agNULL;
64 dmIntContext_t *dmAllShared = agNULL;
65 dmIntPortContext_t *onePortContext = agNULL;
66 dmList_t *PortContextList = agNULL;
67
68 DM_DBG3(("dmCreatePort: start\n"));
69
70 if (dmRoot == agNULL)
71 {
72 DM_DBG1(("dmCreatePort: dmRoot is NULL, wrong!!!\n"));
73 return DM_RC_FAILURE;
74 }
75
76 if (dmPortContext == agNULL)
77 {
78 DM_DBG1(("dmCreatePort: dmPortContext is NULL, wrong!!!\n"));
79 return DM_RC_FAILURE;
80 }
81
82 /* the duplicacy of a port is checked */
83 if (dmPortContext->dmData != agNULL)
84 {
85 DM_DBG1(("dmCreatePort: dmPortContext->dmData is not NULL, wrong, Already created!!!\n"));
86 return DM_RC_FAILURE;
87 }
88
89 if (dmPortInfo == agNULL)
90 {
91 DM_DBG1(("dmCreatePort: dmPortInfo is NULL, wrong!!!\n"));
92 return DM_RC_FAILURE;
93 }
94
95 dmIntRoot = (dmIntRoot_t *)dmRoot->dmData;
96
97 if (dmIntRoot == agNULL)
98 {
99 DM_DBG1(("dmCreatePort: dmIntRoot is NULL, wrong!!!\n"));
100 return DM_RC_FAILURE;
101 }
102
103 dmAllShared = (dmIntContext_t *)&dmIntRoot->dmAllShared;
104
105 if (dmAllShared == agNULL)
106 {
107 DM_DBG1(("dmCreatePort: dmAllShared is NULL, wrong!!!\n"));
108 return DM_RC_FAILURE;
109 }
110
111 tddmSingleThreadedEnter(dmRoot, DM_PORT_LOCK);
112 if (DMLIST_NOT_EMPTY(&(dmAllShared->FreePortContextList)))
113 {
114 DMLIST_DEQUEUE_FROM_HEAD(&PortContextList, &(dmAllShared->FreePortContextList));
115 tddmSingleThreadedLeave(dmRoot, DM_PORT_LOCK);
116 onePortContext = DMLIST_OBJECT_BASE(dmIntPortContext_t, FreeLink, PortContextList);
117 if (onePortContext == agNULL)
118 {
119 DM_DBG1(("dmCreatePort: onePortContext is NULL in allocation, wrong!!!\n"));
120 return DM_RC_FAILURE;
121 }
122
123 dmPortContext->dmData = onePortContext;
124 onePortContext->DiscoveryState = DM_DSTATE_NOT_STARTED;
125 onePortContext->discoveryOptions = DM_DISCOVERY_OPTION_FULL_START;
126
127 onePortContext->dmRoot = dmRoot;
128 onePortContext->dmPortContext = dmPortContext;
129 onePortContext->valid = agTRUE;
130 onePortContext->RegFailed = agFALSE;
131
132 onePortContext->LinkRate = DM_GET_LINK_RATE(dmPortInfo->flag);
133 DM_DBG3(("dmCreatePort: linkrate %0x\n", onePortContext->LinkRate));
134
135 onePortContext->sasRemoteAddressHi = DM_GET_SAS_ADDRESSHI(dmPortInfo->sasRemoteAddressHi);
136 onePortContext->sasRemoteAddressLo = DM_GET_SAS_ADDRESSLO(dmPortInfo->sasRemoteAddressLo);
137 onePortContext->sasLocalAddressHi = DM_GET_SAS_ADDRESSHI(dmPortInfo->sasLocalAddressHi);
138 onePortContext->sasLocalAddressLo = DM_GET_SAS_ADDRESSLO(dmPortInfo->sasLocalAddressLo);
139 DM_DBG3(("dmCreatePort: pid %d\n", onePortContext->id));
140 DM_DBG3(("dmCreatePort: RemoteAddrHi 0x%08x RemoteAddrLo 0x%08x\n", onePortContext->sasRemoteAddressHi, onePortContext->sasRemoteAddressLo));
141 DM_DBG3(("dmCreatePort: LocalAddrHi 0x%08x LocaAddrLo 0x%08x\n", onePortContext->sasLocalAddressHi, onePortContext->sasLocalAddressLo));
142
143 tddmSingleThreadedEnter(dmRoot, DM_PORT_LOCK);
144 DMLIST_ENQUEUE_AT_TAIL(&(onePortContext->MainLink), &(dmAllShared->MainPortContextList));
145 tddmSingleThreadedLeave(dmRoot, DM_PORT_LOCK);
146 }
147 else
148 {
149 tddmSingleThreadedLeave(dmRoot, DM_PORT_LOCK);
150 DM_DBG1(("dmCreatePort: Attention. no more free PortContext!!!\n"));
151 return DM_RC_FAILURE;
152 }
153
154 return DM_RC_SUCCESS;
155 }
156
157 /*****************************************************************************/
158 /*! \brief dmDestroyPort
159 *
160 *
161 * Purpose: A port context is destroyed by this function
162 *
163 * \param dmRoot: DM context handle.
164 * \param dmPortContext: Pointer to this instance of port context
165 *
166 * \return:
167 * DM_RC_SUCCESS
168 * DM_RC_FAILURE
169 *
170 */
171 /*****************************************************************************/
172 osGLOBAL bit32
dmDestroyPort(dmRoot_t * dmRoot,dmPortContext_t * dmPortContext,dmPortInfo_t * dmPortInfo)173 dmDestroyPort(
174 dmRoot_t *dmRoot,
175 dmPortContext_t *dmPortContext,
176 dmPortInfo_t *dmPortInfo)
177 {
178 dmIntRoot_t *dmIntRoot = agNULL;
179 dmIntContext_t *dmAllShared = agNULL;
180 dmIntPortContext_t *onePortContext = agNULL;
181
182 DM_DBG1(("dmDestroyPort: start\n"));
183 if (dmRoot == agNULL)
184 {
185 DM_DBG1(("dmDestroyPort: dmRoot is NULL, wrong!!!\n"));
186 return DM_RC_FAILURE;
187 }
188
189 if (dmPortContext == agNULL)
190 {
191 DM_DBG1(("dmDestroyPort: dmPortContext is NULL, wrong!!!\n"));
192 return DM_RC_FAILURE;
193 }
194
195 if (dmPortInfo == agNULL)
196 {
197 DM_DBG1(("dmDestroyPort: dmPortInfo is NULL, wrong!!!\n"));
198 return DM_RC_FAILURE;
199 }
200
201 dmIntRoot = (dmIntRoot_t *)dmRoot->dmData;
202
203 if (dmIntRoot == agNULL)
204 {
205 DM_DBG1(("dmDestroyPort: dmIntRoot is NULL, wrong!!!\n"));
206 return DM_RC_FAILURE;
207 }
208
209 dmAllShared = (dmIntContext_t *)&dmIntRoot->dmAllShared;
210
211 if (dmAllShared == agNULL)
212 {
213 DM_DBG1(("dmDestroyPort: dmAllShared is NULL, wrong!!!\n"));
214 return DM_RC_FAILURE;
215 }
216
217 /*
218 no device(expander) to be removed since all devices should
219 be in freelist at the end of discovery
220 But if the discovery is in progress, abort it and clean up
221 */
222 onePortContext = (dmIntPortContext_t *)dmPortContext->dmData;
223
224 if (onePortContext == agNULL)
225 {
226 DM_DBG1(("dmDestroyPort: onePortContext is NULL, wrong!!!\n"));
227 return DM_RC_FAILURE;
228 }
229
230 #if 1
231 if (onePortContext->DiscoveryState != DM_DSTATE_COMPLETED)
232 {
233 dmDiscoverAbort(dmRoot, onePortContext);
234 }
235 else
236 {
237 /* move devices from dmAllShared->MainDeviceList to dmAllShared->FreeDeviceList; dmDiscoveryDeviceCleanUp()
238 move from dmAllShared->mainExpanderList to dmAllShared->freeExpanderList; dmDiscoveryExpanderCleanUp()
239 */
240 }
241 #endif
242
243 if (onePortContext->DiscoveryState != DM_DSTATE_COMPLETED)
244 {
245 /* move from dmAllShared->discoveringExpanderList to dmAllShared->mainExpanderList
246 move from dmAllShared->UpdiscoveringExpanderList to dmAllShared->mainExpanderList
247 */
248 dmCleanAllExp(dmRoot, onePortContext);
249 }
250
251 /* move mainExpanderList then MainDeviceList */
252 DM_DBG3(("dmDestroyPort: before dmDiscoveryExpanderCleanUp\n"));
253 dmDumpAllMainExp(dmRoot, onePortContext);
254
255 /* move from dmAllShared->mainExpanderList to dmAllShared->freeExpanderList */
256 dmDiscoveryExpanderCleanUp(dmRoot, onePortContext);
257
258 DM_DBG3(("dmDestroyPort: after dmDiscoveryExpanderCleanUp\n"));
259 dmDumpAllMainExp(dmRoot, onePortContext);
260
261 DM_DBG3(("dmDestroyPort: before dmDiscoveryDeviceCleanUp\n"));
262 dmDumpAllMainDevice(dmRoot, onePortContext);
263 /* move devices from dmAllShared->MainDeviceList to dmAllShared->FreeDeviceList */
264 dmDiscoveryDeviceCleanUp(dmRoot, onePortContext);
265
266 DM_DBG3(("dmDestroyPort: after dmDiscoveryDeviceCleanUp\n"));
267 dmDumpAllMainDevice(dmRoot, onePortContext);
268
269 dmPortContextReInit(dmRoot, onePortContext);
270
271 tddmSingleThreadedEnter(dmRoot, DM_PORT_LOCK);
272
273 if (DMLIST_NOT_EMPTY(&(onePortContext->MainLink)))
274 {
275 DMLIST_DEQUEUE_THIS(&(onePortContext->MainLink));
276 }
277 else
278 {
279 DM_DBG1(("dmDestroyPort: onePortContext->MainLink is NULL, wrong!!!\n"));
280 }
281
282 if (DMLIST_NOT_EMPTY(&(onePortContext->FreeLink)) && DMLIST_NOT_EMPTY(&(dmAllShared->FreePortContextList)))
283 {
284 DMLIST_ENQUEUE_AT_TAIL(&(onePortContext->FreeLink), &(dmAllShared->FreePortContextList));
285 }
286 else
287 {
288 DM_DBG1(("dmDestroyPort: onePortContext->FreeLink or dmAllShared->FreePortContextList is NULL, wrong!!!\n"));
289 }
290
291 tddmSingleThreadedLeave(dmRoot, DM_PORT_LOCK);
292
293 return DM_RC_SUCCESS;
294 }
295 #endif /* FDS_ DM */
296
297
298
299
300
301
302
303
304