|
@@ -495,39 +495,24 @@ int mei_hbm_cl_disconnect_rsp(struct mei_device *dev, struct mei_cl *cl)
|
|
}
|
|
}
|
|
|
|
|
|
/**
|
|
/**
|
|
- * mei_hbm_cl_disconnect_res - disconnect response from ME
|
|
|
|
|
|
+ * mei_hbm_cl_disconnect_res - update the client state according
|
|
|
|
+ * disconnect response
|
|
*
|
|
*
|
|
- * @dev: the device structure
|
|
|
|
- * @rs: disconnect response bus message
|
|
|
|
|
|
+ * @cl: mei host client
|
|
|
|
+ * @cmd: disconnect client response host bus message
|
|
*/
|
|
*/
|
|
-static void mei_hbm_cl_disconnect_res(struct mei_device *dev,
|
|
|
|
- struct hbm_client_connect_response *rs)
|
|
|
|
|
|
+static void mei_hbm_cl_disconnect_res(struct mei_cl *cl,
|
|
|
|
+ struct mei_hbm_cl_cmd *cmd)
|
|
{
|
|
{
|
|
- struct mei_cl *cl;
|
|
|
|
- struct mei_cl_cb *cb, *next;
|
|
|
|
|
|
+ struct hbm_client_connect_response *rs =
|
|
|
|
+ (struct hbm_client_connect_response *)cmd;
|
|
|
|
|
|
- dev_dbg(&dev->pdev->dev, "hbm: disconnect response cl:host=%02d me=%02d status=%d\n",
|
|
|
|
|
|
+ dev_dbg(&cl->dev->pdev->dev, "hbm: disconnect response cl:host=%02d me=%02d status=%d\n",
|
|
rs->me_addr, rs->host_addr, rs->status);
|
|
rs->me_addr, rs->host_addr, rs->status);
|
|
|
|
|
|
- list_for_each_entry_safe(cb, next, &dev->ctrl_rd_list.list, list) {
|
|
|
|
- cl = cb->cl;
|
|
|
|
-
|
|
|
|
- /* this should not happen */
|
|
|
|
- if (WARN_ON(!cl)) {
|
|
|
|
- list_del(&cb->list);
|
|
|
|
- return;
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- if (mei_hbm_cl_addr_equal(cl, rs)) {
|
|
|
|
- list_del(&cb->list);
|
|
|
|
- if (rs->status == MEI_CL_DISCONN_SUCCESS)
|
|
|
|
- cl->state = MEI_FILE_DISCONNECTED;
|
|
|
|
-
|
|
|
|
- cl->status = 0;
|
|
|
|
- cl->timer_count = 0;
|
|
|
|
- break;
|
|
|
|
- }
|
|
|
|
- }
|
|
|
|
|
|
+ if (rs->status == MEI_CL_DISCONN_SUCCESS)
|
|
|
|
+ cl->state = MEI_FILE_DISCONNECTED;
|
|
|
|
+ cl->status = 0;
|
|
}
|
|
}
|
|
|
|
|
|
/**
|
|
/**
|
|
@@ -545,24 +530,45 @@ int mei_hbm_cl_connect_req(struct mei_device *dev, struct mei_cl *cl)
|
|
}
|
|
}
|
|
|
|
|
|
/**
|
|
/**
|
|
- * mei_hbm_cl_connect_res - connect response from the ME
|
|
|
|
|
|
+ * mei_hbm_cl_connect_res - update the client state according
|
|
|
|
+ * connection response
|
|
*
|
|
*
|
|
- * @dev: the device structure
|
|
|
|
- * @rs: connect response bus message
|
|
|
|
|
|
+ * @cl: mei host client
|
|
|
|
+ * @cmd: connect client response host bus message
|
|
*/
|
|
*/
|
|
-static void mei_hbm_cl_connect_res(struct mei_device *dev,
|
|
|
|
- struct hbm_client_connect_response *rs)
|
|
|
|
|
|
+static void mei_hbm_cl_connect_res(struct mei_cl *cl,
|
|
|
|
+ struct mei_hbm_cl_cmd *cmd)
|
|
{
|
|
{
|
|
|
|
+ struct hbm_client_connect_response *rs =
|
|
|
|
+ (struct hbm_client_connect_response *)cmd;
|
|
|
|
|
|
- struct mei_cl *cl;
|
|
|
|
- struct mei_cl_cb *cb, *next;
|
|
|
|
-
|
|
|
|
- dev_dbg(&dev->pdev->dev, "hbm: connect response cl:host=%02d me=%02d status=%s\n",
|
|
|
|
|
|
+ dev_dbg(&cl->dev->pdev->dev, "hbm: connect response cl:host=%02d me=%02d status=%s\n",
|
|
rs->me_addr, rs->host_addr,
|
|
rs->me_addr, rs->host_addr,
|
|
mei_cl_conn_status_str(rs->status));
|
|
mei_cl_conn_status_str(rs->status));
|
|
|
|
|
|
- cl = NULL;
|
|
|
|
|
|
+ if (rs->status == MEI_CL_CONN_SUCCESS)
|
|
|
|
+ cl->state = MEI_FILE_CONNECTED;
|
|
|
|
+ else
|
|
|
|
+ cl->state = MEI_FILE_DISCONNECTED;
|
|
|
|
+ cl->status = mei_cl_conn_status_to_errno(rs->status);
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+/**
|
|
|
|
+ * mei_hbm_cl_res - process hbm response received on behalf
|
|
|
|
+ * an client
|
|
|
|
+ *
|
|
|
|
+ * @dev: the device structure
|
|
|
|
+ * @rs: hbm client message
|
|
|
|
+ * @fop_type: file operation type
|
|
|
|
+ */
|
|
|
|
+static void mei_hbm_cl_res(struct mei_device *dev,
|
|
|
|
+ struct mei_hbm_cl_cmd *rs,
|
|
|
|
+ enum mei_cb_file_ops fop_type)
|
|
|
|
+{
|
|
|
|
+ struct mei_cl *cl;
|
|
|
|
+ struct mei_cl_cb *cb, *next;
|
|
|
|
|
|
|
|
+ cl = NULL;
|
|
list_for_each_entry_safe(cb, next, &dev->ctrl_rd_list.list, list) {
|
|
list_for_each_entry_safe(cb, next, &dev->ctrl_rd_list.list, list) {
|
|
|
|
|
|
cl = cb->cl;
|
|
cl = cb->cl;
|
|
@@ -572,7 +578,7 @@ static void mei_hbm_cl_connect_res(struct mei_device *dev,
|
|
continue;
|
|
continue;
|
|
}
|
|
}
|
|
|
|
|
|
- if (cb->fop_type != MEI_FOP_CONNECT)
|
|
|
|
|
|
+ if (cb->fop_type != fop_type)
|
|
continue;
|
|
continue;
|
|
|
|
|
|
if (mei_hbm_cl_addr_equal(cl, rs)) {
|
|
if (mei_hbm_cl_addr_equal(cl, rs)) {
|
|
@@ -584,12 +590,19 @@ static void mei_hbm_cl_connect_res(struct mei_device *dev,
|
|
if (!cl)
|
|
if (!cl)
|
|
return;
|
|
return;
|
|
|
|
|
|
|
|
+ switch (fop_type) {
|
|
|
|
+ case MEI_FOP_CONNECT:
|
|
|
|
+ mei_hbm_cl_connect_res(cl, rs);
|
|
|
|
+ break;
|
|
|
|
+ case MEI_FOP_DISCONNECT:
|
|
|
|
+ mei_hbm_cl_disconnect_res(cl, rs);
|
|
|
|
+ break;
|
|
|
|
+ default:
|
|
|
|
+ return;
|
|
|
|
+ }
|
|
|
|
+
|
|
cl->timer_count = 0;
|
|
cl->timer_count = 0;
|
|
- if (rs->status == MEI_CL_CONN_SUCCESS)
|
|
|
|
- cl->state = MEI_FILE_CONNECTED;
|
|
|
|
- else
|
|
|
|
- cl->state = MEI_FILE_DISCONNECTED;
|
|
|
|
- cl->status = mei_cl_conn_status_to_errno(rs->status);
|
|
|
|
|
|
+ wake_up(&cl->wait);
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
@@ -657,17 +670,18 @@ int mei_hbm_dispatch(struct mei_device *dev, struct mei_msg_hdr *hdr)
|
|
{
|
|
{
|
|
struct mei_bus_message *mei_msg;
|
|
struct mei_bus_message *mei_msg;
|
|
struct hbm_host_version_response *version_res;
|
|
struct hbm_host_version_response *version_res;
|
|
- struct hbm_client_connect_response *connect_res;
|
|
|
|
- struct hbm_client_connect_response *disconnect_res;
|
|
|
|
- struct hbm_client_connect_request *disconnect_req;
|
|
|
|
- struct hbm_flow_control *flow_control;
|
|
|
|
struct hbm_props_response *props_res;
|
|
struct hbm_props_response *props_res;
|
|
struct hbm_host_enum_response *enum_res;
|
|
struct hbm_host_enum_response *enum_res;
|
|
|
|
|
|
|
|
+ struct mei_hbm_cl_cmd *cl_cmd;
|
|
|
|
+ struct hbm_client_connect_request *disconnect_req;
|
|
|
|
+ struct hbm_flow_control *flow_control;
|
|
|
|
+
|
|
/* read the message to our buffer */
|
|
/* read the message to our buffer */
|
|
BUG_ON(hdr->length >= sizeof(dev->rd_msg_buf));
|
|
BUG_ON(hdr->length >= sizeof(dev->rd_msg_buf));
|
|
mei_read_slots(dev, dev->rd_msg_buf, hdr->length);
|
|
mei_read_slots(dev, dev->rd_msg_buf, hdr->length);
|
|
mei_msg = (struct mei_bus_message *)dev->rd_msg_buf;
|
|
mei_msg = (struct mei_bus_message *)dev->rd_msg_buf;
|
|
|
|
+ cl_cmd = (struct mei_hbm_cl_cmd *)mei_msg;
|
|
|
|
|
|
/* ignore spurious message and prevent reset nesting
|
|
/* ignore spurious message and prevent reset nesting
|
|
* hbm is put to idle during system reset
|
|
* hbm is put to idle during system reset
|
|
@@ -730,18 +744,12 @@ int mei_hbm_dispatch(struct mei_device *dev, struct mei_msg_hdr *hdr)
|
|
|
|
|
|
case CLIENT_CONNECT_RES_CMD:
|
|
case CLIENT_CONNECT_RES_CMD:
|
|
dev_dbg(&dev->pdev->dev, "hbm: client connect response: message received.\n");
|
|
dev_dbg(&dev->pdev->dev, "hbm: client connect response: message received.\n");
|
|
-
|
|
|
|
- connect_res = (struct hbm_client_connect_response *) mei_msg;
|
|
|
|
- mei_hbm_cl_connect_res(dev, connect_res);
|
|
|
|
- wake_up(&dev->wait_recvd_msg);
|
|
|
|
|
|
+ mei_hbm_cl_res(dev, cl_cmd, MEI_FOP_CONNECT);
|
|
break;
|
|
break;
|
|
|
|
|
|
case CLIENT_DISCONNECT_RES_CMD:
|
|
case CLIENT_DISCONNECT_RES_CMD:
|
|
dev_dbg(&dev->pdev->dev, "hbm: client disconnect response: message received.\n");
|
|
dev_dbg(&dev->pdev->dev, "hbm: client disconnect response: message received.\n");
|
|
-
|
|
|
|
- disconnect_res = (struct hbm_client_connect_response *) mei_msg;
|
|
|
|
- mei_hbm_cl_disconnect_res(dev, disconnect_res);
|
|
|
|
- wake_up(&dev->wait_recvd_msg);
|
|
|
|
|
|
+ mei_hbm_cl_res(dev, cl_cmd, MEI_FOP_DISCONNECT);
|
|
break;
|
|
break;
|
|
|
|
|
|
case MEI_FLOW_CONTROL_CMD:
|
|
case MEI_FLOW_CONTROL_CMD:
|