1221167Sgnn/*-
2221167Sgnn * Copyright(c) 2002-2011 Exar Corp.
3221167Sgnn * All rights reserved.
4221167Sgnn *
5221167Sgnn * Redistribution and use in source and binary forms, with or without
6221167Sgnn * modification are permitted provided the following conditions are met:
7221167Sgnn *
8221167Sgnn *    1. Redistributions of source code must retain the above copyright notice,
9221167Sgnn *       this list of conditions and the following disclaimer.
10221167Sgnn *
11221167Sgnn *    2. Redistributions in binary form must reproduce the above copyright
12221167Sgnn *       notice, this list of conditions and the following disclaimer in the
13221167Sgnn *       documentation and/or other materials provided with the distribution.
14221167Sgnn *
15221167Sgnn *    3. Neither the name of the Exar Corporation nor the names of its
16221167Sgnn *       contributors may be used to endorse or promote products derived from
17221167Sgnn *       this software without specific prior written permission.
18221167Sgnn *
19221167Sgnn * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
20221167Sgnn * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
21221167Sgnn * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
22221167Sgnn * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
23221167Sgnn * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24221167Sgnn * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25221167Sgnn * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26221167Sgnn * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27221167Sgnn * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28221167Sgnn * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29221167Sgnn * POSSIBILITY OF SUCH DAMAGE.
30221167Sgnn */
31221167Sgnn/*$FreeBSD$*/
32221167Sgnn#include <dev/vxge/vxgehal/vxgehal.h>
33221167Sgnn
34221167Sgnn/*
35221167Sgnn * __hal_ifmsg_wmsg_process - Process the srpcim to vpath wmsg
36221167Sgnn * @vpath: vpath
37221167Sgnn * @wmsg: wsmsg
38221167Sgnn *
39221167Sgnn * Processes the wmsg and invokes appropriate action
40221167Sgnn */
41221167Sgnnvoid
42221167Sgnn__hal_ifmsg_wmsg_process(
43221167Sgnn    __hal_virtualpath_t *vpath,
44221167Sgnn    u64 wmsg)
45221167Sgnn{
46221167Sgnn	u32 msg_type;
47221167Sgnn	__hal_device_t *hldev = vpath->hldev;
48221167Sgnn
49221167Sgnn	vxge_assert(vpath);
50221167Sgnn
51221167Sgnn	vxge_hal_trace_log_vpath("==> %s:%s:%d",
52221167Sgnn	    __FILE__, __func__, __LINE__);
53221167Sgnn
54221167Sgnn	vxge_hal_trace_log_vpath("vpath = 0x"VXGE_OS_STXFMT
55221167Sgnn	    ",wmsg = 0x"VXGE_OS_LLXFMT"", (ptr_t) vpath, wmsg);
56221167Sgnn
57221167Sgnn	if ((vpath->vp_id != vpath->hldev->first_vp_id) ||
58221167Sgnn	    (vpath->hldev->vpath_assignments &
59221167Sgnn	    mBIT((u32) VXGE_HAL_RTS_ACCESS_STEER_DATA0_GET_MSG_SRC(wmsg)))) {
60221167Sgnn		vxge_hal_trace_log_vpath("<== %s:%s:%d Result = 0",
61221167Sgnn		    __FILE__, __func__, __LINE__);
62221167Sgnn		return;
63221167Sgnn	}
64221167Sgnn
65221167Sgnn	msg_type = (u32) VXGE_HAL_RTS_ACCESS_STEER_DATA0_GET_MSG_TYPE(wmsg);
66221167Sgnn
67221167Sgnn	switch (msg_type) {
68221167Sgnn	default:
69221167Sgnn	case VXGE_HAL_RTS_ACCESS_STEER_DATA0_MSG_TYPE_UNKNOWN:
70221167Sgnn		break;
71221167Sgnn	case VXGE_HAL_RTS_ACCESS_STEER_DATA0_MSG_TYPE_DEVICE_RESET_BEGIN:
72221167Sgnn		__hal_device_handle_error(hldev,
73221167Sgnn		    vpath->vp_id,
74221167Sgnn		    VXGE_HAL_EVENT_DEVICE_RESET_START);
75221167Sgnn		break;
76221167Sgnn	case VXGE_HAL_RTS_ACCESS_STEER_DATA0_MSG_TYPE_DEVICE_RESET_END:
77221167Sgnn		vpath->hldev->manager_up = TRUE;
78221167Sgnn		__hal_device_handle_error(hldev,
79221167Sgnn		    vpath->vp_id,
80221167Sgnn		    VXGE_HAL_EVENT_DEVICE_RESET_COMPLETE);
81221167Sgnn		break;
82221167Sgnn	case VXGE_HAL_RTS_ACCESS_STEER_DATA0_MSG_TYPE_VPATH_RESET_BEGIN:
83221167Sgnn		__hal_device_handle_error(hldev,
84221167Sgnn		    vpath->vp_id,
85221167Sgnn		    VXGE_HAL_EVENT_VPATH_RESET_START);
86221167Sgnn		break;
87221167Sgnn	case VXGE_HAL_RTS_ACCESS_STEER_DATA0_MSG_TYPE_VPATH_RESET_END:
88221167Sgnn		vpath->hldev->manager_up = TRUE;
89221167Sgnn		__hal_device_handle_error(hldev,
90221167Sgnn		    vpath->vp_id,
91221167Sgnn		    VXGE_HAL_EVENT_VPATH_RESET_COMPLETE);
92221167Sgnn		break;
93221167Sgnn	case VXGE_HAL_RTS_ACCESS_STEER_DATA0_MSG_TYPE_PRIV_DRIVER_UP:
94221167Sgnn		vpath->hldev->manager_up = TRUE;
95221167Sgnn		break;
96221167Sgnn	case VXGE_HAL_RTS_ACCESS_STEER_DATA0_MSG_TYPE_PRIV_DRIVER_DOWN:
97221167Sgnn		vpath->hldev->manager_up = FALSE;
98221167Sgnn		break;
99221167Sgnn	case VXGE_HAL_RTS_ACCESS_STEER_DATA0_MSG_TYPE_ACK:
100221167Sgnn		break;
101221167Sgnn	}
102221167Sgnn
103221167Sgnn	vxge_hal_trace_log_vpath("<== %s:%s:%d Result = 0",
104221167Sgnn	    __FILE__, __func__, __LINE__);
105221167Sgnn}
106221167Sgnn
107221167Sgnn/*
108221167Sgnn * __hal_ifmsg_device_reset_end_poll - Polls for the
109221167Sgnn *			     srpcim to vpath reset end
110221167Sgnn * @hldev: HAL Device
111221167Sgnn * @vp_id: Vpath id
112221167Sgnn *
113221167Sgnn * Polls for the srpcim to vpath reset end
114221167Sgnn */
115221167Sgnnvxge_hal_status_e
116221167Sgnn__hal_ifmsg_device_reset_end_poll(
117221167Sgnn    __hal_device_t *hldev,
118221167Sgnn    u32 vp_id)
119221167Sgnn{
120221167Sgnn	vxge_hal_status_e status;
121221167Sgnn
122221167Sgnn	vxge_assert(hldev);
123221167Sgnn
124221167Sgnn	vxge_hal_trace_log_mrpcim("==> %s:%s:%d",
125221167Sgnn	    __FILE__, __func__, __LINE__);
126221167Sgnn
127221167Sgnn	vxge_hal_trace_log_mrpcim("hldev = 0x"VXGE_OS_STXFMT", vp_id = %d",
128221167Sgnn	    (ptr_t) hldev, vp_id);
129221167Sgnn
130221167Sgnn	status = vxge_hal_device_register_poll(
131221167Sgnn	    hldev->header.pdev,
132221167Sgnn	    hldev->header.regh0,
133221167Sgnn	    &hldev->vpmgmt_reg[vp_id]->srpcim_to_vpath_wmsg, 0,
134221167Sgnn	    ~((u64) VXGE_HAL_IFMSG_DEVICE_RESET_END_MSG),
135221167Sgnn	    WAIT_FACTOR * hldev->header.config.device_poll_millis);
136221167Sgnn
137221167Sgnn	vxge_hal_trace_log_mrpcim("<== %s:%s:%d Result = 0",
138221167Sgnn	    __FILE__, __func__, __LINE__);
139221167Sgnn
140221167Sgnn	return (status);
141221167Sgnn
142221167Sgnn}
143221167Sgnn
144221167Sgnn/*
145221167Sgnn * __hal_ifmsg_wmsg_post - Posts the srpcim to vpath req
146221167Sgnn * @hldev: Hal device
147221167Sgnn * @src_vp_id: Source vpath id
148221167Sgnn * @dest_vp_id: Vpath id, VXGE_HAL_RTS_ACCESS_STEER_MSG_DEST_MRPCIM, or
149221167Sgnn *	    VXGE_HAL_RTS_ACCESS_STEER_MSG_DEST_BROADCAST
150221167Sgnn * @msg_type: wsmsg type
151221167Sgnn * @msg_data: wsmsg data
152221167Sgnn *
153221167Sgnn * Posts the req
154221167Sgnn */
155221167Sgnnvxge_hal_status_e
156221167Sgnn__hal_ifmsg_wmsg_post(
157221167Sgnn    __hal_device_t *hldev,
158221167Sgnn    u32 src_vp_id,
159221167Sgnn    u32 dest_vp_id,
160221167Sgnn    u32 msg_type,
161221167Sgnn    u32 msg_data)
162221167Sgnn{
163221167Sgnn	u64 val64;
164221167Sgnn	vxge_hal_vpath_reg_t *vp_reg;
165221167Sgnn	vxge_hal_status_e status;
166221167Sgnn
167221167Sgnn	vxge_assert(hldev);
168221167Sgnn
169221167Sgnn	vp_reg = hldev->vpath_reg[src_vp_id];
170221167Sgnn
171221167Sgnn	vxge_hal_trace_log_vpath("==> %s:%s:%d",
172221167Sgnn	    __FILE__, __func__, __LINE__);
173221167Sgnn
174221167Sgnn	vxge_hal_trace_log_srpcim(
175221167Sgnn	    "hldev = 0x"VXGE_OS_STXFMT", src_vp_id = %d, dest_vp_id = %d, "
176221167Sgnn	    "msg_type = %d, msg_data = %d", (ptr_t) hldev, src_vp_id,
177221167Sgnn	    dest_vp_id, msg_type, msg_data);
178221167Sgnn
179221167Sgnn	vxge_os_pio_mem_write64(hldev->header.pdev,
180221167Sgnn	    hldev->header.regh0,
181221167Sgnn	    0,
182221167Sgnn	    &vp_reg->rts_access_steer_ctrl);
183221167Sgnn
184221167Sgnn	vxge_os_wmb();
185221167Sgnn
186221167Sgnn
187221167Sgnn	vxge_os_pio_mem_write64(hldev->header.pdev,
188221167Sgnn	    hldev->header.regh0,
189221167Sgnn	    VXGE_HAL_RTS_ACCESS_STEER_DATA0_IGNORE_IN_SVC_CHECK |
190221167Sgnn	    VXGE_HAL_RTS_ACCESS_STEER_DATA0_MSG_TYPE(msg_type) |
191221167Sgnn	    VXGE_HAL_RTS_ACCESS_STEER_DATA0_MSG_DEST(dest_vp_id) |
192221167Sgnn	    VXGE_HAL_RTS_ACCESS_STEER_DATA0_MSG_SRC(src_vp_id) |
193221167Sgnn	    VXGE_HAL_RTS_ACCESS_STEER_DATA0_SEQ_NUM(++hldev->ifmsg_seqno) |
194221167Sgnn	    VXGE_HAL_RTS_ACCESS_STEER_DATA0_MSG_DATA(msg_data),
195221167Sgnn	    &vp_reg->rts_access_steer_data0);
196221167Sgnn
197221167Sgnn	vxge_os_pio_mem_write64(hldev->header.pdev,
198221167Sgnn	    hldev->header.regh0,
199221167Sgnn	    0,
200221167Sgnn	    &vp_reg->rts_access_steer_data1);
201221167Sgnn
202221167Sgnn	vxge_os_wmb();
203221167Sgnn
204221167Sgnn	val64 = VXGE_HAL_RTS_ACCESS_STEER_CTRL_ACTION(
205221167Sgnn	    VXGE_HAL_RTS_ACCESS_STEER_CTRL_ACTION_SEND_MSG) |
206221167Sgnn	    VXGE_HAL_RTS_ACCESS_STEER_CTRL_DATA_STRUCT_SEL(
207221167Sgnn	    VXGE_HAL_RTS_ACCESS_STEER_CTRL_DATA_STRUCT_SEL_FW_MEMO) |
208221167Sgnn	    VXGE_HAL_RTS_ACCESS_STEER_CTRL_STROBE |
209221167Sgnn	    VXGE_HAL_RTS_ACCESS_STEER_CTRL_OFFSET(0);
210221167Sgnn
211221167Sgnn	vxge_hal_pio_mem_write32_lower(hldev->header.pdev,
212221167Sgnn	    hldev->header.regh0,
213221167Sgnn	    (u32) bVAL32(val64, 32),
214221167Sgnn	    &vp_reg->rts_access_steer_ctrl);
215221167Sgnn
216221167Sgnn	vxge_os_wmb();
217221167Sgnn
218221167Sgnn	vxge_hal_pio_mem_write32_upper(hldev->header.pdev,
219221167Sgnn	    hldev->header.regh0,
220221167Sgnn	    (u32) bVAL32(val64, 0),
221221167Sgnn	    &vp_reg->rts_access_steer_ctrl);
222221167Sgnn
223221167Sgnn	vxge_os_wmb();
224221167Sgnn
225221167Sgnn	status = vxge_hal_device_register_poll(hldev->header.pdev,
226221167Sgnn	    hldev->header.regh0,
227221167Sgnn	    &vp_reg->rts_access_steer_ctrl, 0,
228221167Sgnn	    VXGE_HAL_RTS_ACCESS_STEER_CTRL_STROBE,
229221167Sgnn	    WAIT_FACTOR * hldev->header.config.device_poll_millis);
230221167Sgnn
231221167Sgnn	if (status != VXGE_HAL_OK) {
232221167Sgnn
233221167Sgnn		vxge_hal_trace_log_driver("<== %s:%s:%d  Result: %d",
234221167Sgnn		    __FILE__, __func__, __LINE__, status);
235221167Sgnn		return (status);
236221167Sgnn	}
237221167Sgnn
238221167Sgnn	val64 = vxge_os_pio_mem_read64(hldev->header.pdev,
239221167Sgnn	    hldev->header.regh0,
240221167Sgnn	    &vp_reg->rts_access_steer_ctrl);
241221167Sgnn
242221167Sgnn	if (val64 & VXGE_HAL_RTS_ACCESS_STEER_CTRL_RMACJ_STATUS) {
243221167Sgnn
244221167Sgnn		vxge_os_pio_mem_read64(hldev->header.pdev,
245221167Sgnn		    hldev->header.regh0,
246221167Sgnn		    &vp_reg->rts_access_steer_data0);
247221167Sgnn
248221167Sgnn		status = VXGE_HAL_OK;
249221167Sgnn
250221167Sgnn	} else {
251221167Sgnn		status = VXGE_HAL_FAIL;
252221167Sgnn	}
253221167Sgnn
254221167Sgnn	vxge_hal_trace_log_srpcim("<== %s:%s:%d Result = %d",
255221167Sgnn	    __FILE__, __func__, __LINE__, status);
256221167Sgnn
257221167Sgnn	return (status);
258221167Sgnn}
259