Commit 43645ce0 authored by Sudarsana Reddy Kalluru's avatar Sudarsana Reddy Kalluru Committed by David S. Miller

qed: Populate nvm image attribute shadow.

This patch adds support for populating the flash image attributes.
Signed-off-by: default avatarSudarsana Reddy Kalluru <Sudarsana.Kalluru@cavium.com>
Signed-off-by: default avatarAriel Elior <ariel.elior@cavium.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 50bc60cb
...@@ -437,6 +437,11 @@ enum BAR_ID { ...@@ -437,6 +437,11 @@ enum BAR_ID {
BAR_ID_1 /* Used for doorbells */ BAR_ID_1 /* Used for doorbells */
}; };
struct qed_nvm_image_info {
u32 num_images;
struct bist_nvm_image_att *image_att;
};
#define DRV_MODULE_VERSION \ #define DRV_MODULE_VERSION \
__stringify(QED_MAJOR_VERSION) "." \ __stringify(QED_MAJOR_VERSION) "." \
__stringify(QED_MINOR_VERSION) "." \ __stringify(QED_MINOR_VERSION) "." \
...@@ -561,6 +566,9 @@ struct qed_hwfn { ...@@ -561,6 +566,9 @@ struct qed_hwfn {
/* L2-related */ /* L2-related */
struct qed_l2_info *p_l2_info; struct qed_l2_info *p_l2_info;
/* Nvm images number and attributes */
struct qed_nvm_image_info nvm_info;
struct qed_ptt *p_arfs_ptt; struct qed_ptt *p_arfs_ptt;
struct qed_simd_fp_handler simd_proto_handler[64]; struct qed_simd_fp_handler simd_proto_handler[64];
......
...@@ -2932,6 +2932,12 @@ static int qed_get_dev_info(struct qed_hwfn *p_hwfn, struct qed_ptt *p_ptt) ...@@ -2932,6 +2932,12 @@ static int qed_get_dev_info(struct qed_hwfn *p_hwfn, struct qed_ptt *p_ptt)
return 0; return 0;
} }
static void qed_nvm_info_free(struct qed_hwfn *p_hwfn)
{
kfree(p_hwfn->nvm_info.image_att);
p_hwfn->nvm_info.image_att = NULL;
}
static int qed_hw_prepare_single(struct qed_hwfn *p_hwfn, static int qed_hw_prepare_single(struct qed_hwfn *p_hwfn,
void __iomem *p_regview, void __iomem *p_regview,
void __iomem *p_doorbells, void __iomem *p_doorbells,
...@@ -2995,12 +3001,25 @@ static int qed_hw_prepare_single(struct qed_hwfn *p_hwfn, ...@@ -2995,12 +3001,25 @@ static int qed_hw_prepare_single(struct qed_hwfn *p_hwfn,
DP_NOTICE(p_hwfn, "Failed to initiate PF FLR\n"); DP_NOTICE(p_hwfn, "Failed to initiate PF FLR\n");
} }
/* NVRAM info initialization and population */
if (IS_LEAD_HWFN(p_hwfn)) {
rc = qed_mcp_nvm_info_populate(p_hwfn);
if (rc) {
DP_NOTICE(p_hwfn,
"Failed to populate nvm info shadow\n");
goto err2;
}
}
/* Allocate the init RT array and initialize the init-ops engine */ /* Allocate the init RT array and initialize the init-ops engine */
rc = qed_init_alloc(p_hwfn); rc = qed_init_alloc(p_hwfn);
if (rc) if (rc)
goto err2; goto err3;
return rc; return rc;
err3:
if (IS_LEAD_HWFN(p_hwfn))
qed_nvm_info_free(p_hwfn);
err2: err2:
if (IS_LEAD_HWFN(p_hwfn)) if (IS_LEAD_HWFN(p_hwfn))
qed_iov_free_hw_info(p_hwfn->cdev); qed_iov_free_hw_info(p_hwfn->cdev);
...@@ -3056,6 +3075,7 @@ int qed_hw_prepare(struct qed_dev *cdev, ...@@ -3056,6 +3075,7 @@ int qed_hw_prepare(struct qed_dev *cdev,
if (rc) { if (rc) {
if (IS_PF(cdev)) { if (IS_PF(cdev)) {
qed_init_free(p_hwfn); qed_init_free(p_hwfn);
qed_nvm_info_free(p_hwfn);
qed_mcp_free(p_hwfn); qed_mcp_free(p_hwfn);
qed_hw_hwfn_free(p_hwfn); qed_hw_hwfn_free(p_hwfn);
} }
...@@ -3088,6 +3108,8 @@ void qed_hw_remove(struct qed_dev *cdev) ...@@ -3088,6 +3108,8 @@ void qed_hw_remove(struct qed_dev *cdev)
} }
qed_iov_free_hw_info(cdev); qed_iov_free_hw_info(cdev);
qed_nvm_info_free(p_hwfn);
} }
static void qed_chain_free_next_ptr(struct qed_dev *cdev, static void qed_chain_free_next_ptr(struct qed_dev *cdev,
......
...@@ -2303,9 +2303,9 @@ int qed_mcp_bist_clock_test(struct qed_hwfn *p_hwfn, struct qed_ptt *p_ptt) ...@@ -2303,9 +2303,9 @@ int qed_mcp_bist_clock_test(struct qed_hwfn *p_hwfn, struct qed_ptt *p_ptt)
return rc; return rc;
} }
int qed_mcp_bist_nvm_test_get_num_images(struct qed_hwfn *p_hwfn, int qed_mcp_bist_nvm_get_num_images(struct qed_hwfn *p_hwfn,
struct qed_ptt *p_ptt, struct qed_ptt *p_ptt,
u32 *num_images) u32 *num_images)
{ {
u32 drv_mb_param = 0, rsp; u32 drv_mb_param = 0, rsp;
int rc = 0; int rc = 0;
...@@ -2324,10 +2324,10 @@ int qed_mcp_bist_nvm_test_get_num_images(struct qed_hwfn *p_hwfn, ...@@ -2324,10 +2324,10 @@ int qed_mcp_bist_nvm_test_get_num_images(struct qed_hwfn *p_hwfn,
return rc; return rc;
} }
int qed_mcp_bist_nvm_test_get_image_att(struct qed_hwfn *p_hwfn, int qed_mcp_bist_nvm_get_image_att(struct qed_hwfn *p_hwfn,
struct qed_ptt *p_ptt, struct qed_ptt *p_ptt,
struct bist_nvm_image_att *p_image_att, struct bist_nvm_image_att *p_image_att,
u32 image_index) u32 image_index)
{ {
u32 buf_size = 0, param, resp = 0, resp_param = 0; u32 buf_size = 0, param, resp = 0, resp_param = 0;
int rc; int rc;
...@@ -2351,16 +2351,71 @@ int qed_mcp_bist_nvm_test_get_image_att(struct qed_hwfn *p_hwfn, ...@@ -2351,16 +2351,71 @@ int qed_mcp_bist_nvm_test_get_image_att(struct qed_hwfn *p_hwfn,
return rc; return rc;
} }
int qed_mcp_nvm_info_populate(struct qed_hwfn *p_hwfn)
{
struct qed_nvm_image_info *nvm_info = &p_hwfn->nvm_info;
struct qed_ptt *p_ptt;
int rc;
u32 i;
p_ptt = qed_ptt_acquire(p_hwfn);
if (!p_ptt) {
DP_ERR(p_hwfn, "failed to acquire ptt\n");
return -EBUSY;
}
/* Acquire from MFW the amount of available images */
nvm_info->num_images = 0;
rc = qed_mcp_bist_nvm_get_num_images(p_hwfn,
p_ptt, &nvm_info->num_images);
if (rc == -EOPNOTSUPP) {
DP_INFO(p_hwfn, "DRV_MSG_CODE_BIST_TEST is not supported\n");
goto out;
} else if (rc || !nvm_info->num_images) {
DP_ERR(p_hwfn, "Failed getting number of images\n");
goto err0;
}
nvm_info->image_att = kmalloc(nvm_info->num_images *
sizeof(struct bist_nvm_image_att),
GFP_KERNEL);
if (!nvm_info->image_att) {
rc = -ENOMEM;
goto err0;
}
/* Iterate over images and get their attributes */
for (i = 0; i < nvm_info->num_images; i++) {
rc = qed_mcp_bist_nvm_get_image_att(p_hwfn, p_ptt,
&nvm_info->image_att[i], i);
if (rc) {
DP_ERR(p_hwfn,
"Failed getting image index %d attributes\n", i);
goto err1;
}
DP_VERBOSE(p_hwfn, QED_MSG_SP, "image index %d, size %x\n", i,
nvm_info->image_att[i].len);
}
out:
qed_ptt_release(p_hwfn, p_ptt);
return 0;
err1:
kfree(nvm_info->image_att);
err0:
qed_ptt_release(p_hwfn, p_ptt);
return rc;
}
static int static int
qed_mcp_get_nvm_image_att(struct qed_hwfn *p_hwfn, qed_mcp_get_nvm_image_att(struct qed_hwfn *p_hwfn,
struct qed_ptt *p_ptt, struct qed_ptt *p_ptt,
enum qed_nvm_images image_id, enum qed_nvm_images image_id,
struct qed_nvm_image_att *p_image_att) struct qed_nvm_image_att *p_image_att)
{ {
struct bist_nvm_image_att mfw_image_att;
enum nvm_image_type type; enum nvm_image_type type;
u32 num_images, i; u32 i;
int rc;
/* Translate image_id into MFW definitions */ /* Translate image_id into MFW definitions */
switch (image_id) { switch (image_id) {
...@@ -2376,29 +2431,18 @@ qed_mcp_get_nvm_image_att(struct qed_hwfn *p_hwfn, ...@@ -2376,29 +2431,18 @@ qed_mcp_get_nvm_image_att(struct qed_hwfn *p_hwfn,
return -EINVAL; return -EINVAL;
} }
/* Learn number of images, then traverse and see if one fits */ for (i = 0; i < p_hwfn->nvm_info.num_images; i++)
rc = qed_mcp_bist_nvm_test_get_num_images(p_hwfn, p_ptt, &num_images); if (type == p_hwfn->nvm_info.image_att[i].image_type)
if (rc || !num_images)
return -EINVAL;
for (i = 0; i < num_images; i++) {
rc = qed_mcp_bist_nvm_test_get_image_att(p_hwfn, p_ptt,
&mfw_image_att, i);
if (rc)
return rc;
if (type == mfw_image_att.image_type)
break; break;
} if (i == p_hwfn->nvm_info.num_images) {
if (i == num_images) {
DP_VERBOSE(p_hwfn, QED_MSG_STORAGE, DP_VERBOSE(p_hwfn, QED_MSG_STORAGE,
"Failed to find nvram image of type %08x\n", "Failed to find nvram image of type %08x\n",
image_id); image_id);
return -EINVAL; return -ENOENT;
} }
p_image_att->start_addr = mfw_image_att.nvm_start_addr; p_image_att->start_addr = p_hwfn->nvm_info.image_att[i].nvm_start_addr;
p_image_att->length = mfw_image_att.len; p_image_att->length = p_hwfn->nvm_info.image_att[i].len;
return 0; return 0;
} }
......
...@@ -496,9 +496,9 @@ int qed_mcp_bist_clock_test(struct qed_hwfn *p_hwfn, ...@@ -496,9 +496,9 @@ int qed_mcp_bist_clock_test(struct qed_hwfn *p_hwfn,
* *
* @return int - 0 - operation was successful. * @return int - 0 - operation was successful.
*/ */
int qed_mcp_bist_nvm_test_get_num_images(struct qed_hwfn *p_hwfn, int qed_mcp_bist_nvm_get_num_images(struct qed_hwfn *p_hwfn,
struct qed_ptt *p_ptt, struct qed_ptt *p_ptt,
u32 *num_images); u32 *num_images);
/** /**
* @brief Bist nvm test - get image attributes by index * @brief Bist nvm test - get image attributes by index
...@@ -510,10 +510,10 @@ int qed_mcp_bist_nvm_test_get_num_images(struct qed_hwfn *p_hwfn, ...@@ -510,10 +510,10 @@ int qed_mcp_bist_nvm_test_get_num_images(struct qed_hwfn *p_hwfn,
* *
* @return int - 0 - operation was successful. * @return int - 0 - operation was successful.
*/ */
int qed_mcp_bist_nvm_test_get_image_att(struct qed_hwfn *p_hwfn, int qed_mcp_bist_nvm_get_image_att(struct qed_hwfn *p_hwfn,
struct qed_ptt *p_ptt, struct qed_ptt *p_ptt,
struct bist_nvm_image_att *p_image_att, struct bist_nvm_image_att *p_image_att,
u32 image_index); u32 image_index);
/* Using hwfn number (and not pf_num) is required since in CMT mode, /* Using hwfn number (and not pf_num) is required since in CMT mode,
* same pf_num may be used by two different hwfn * same pf_num may be used by two different hwfn
...@@ -957,4 +957,12 @@ int qed_mcp_get_capabilities(struct qed_hwfn *p_hwfn, struct qed_ptt *p_ptt); ...@@ -957,4 +957,12 @@ int qed_mcp_get_capabilities(struct qed_hwfn *p_hwfn, struct qed_ptt *p_ptt);
* @param p_ptt * @param p_ptt
*/ */
int qed_mcp_set_capabilities(struct qed_hwfn *p_hwfn, struct qed_ptt *p_ptt); int qed_mcp_set_capabilities(struct qed_hwfn *p_hwfn, struct qed_ptt *p_ptt);
/**
* @brief Populate the nvm info shadow in the given hardware function
*
* @param p_hwfn
*/
int qed_mcp_nvm_info_populate(struct qed_hwfn *p_hwfn);
#endif #endif
...@@ -125,7 +125,7 @@ int qed_selftest_nvram(struct qed_dev *cdev) ...@@ -125,7 +125,7 @@ int qed_selftest_nvram(struct qed_dev *cdev)
} }
/* Acquire from MFW the amount of available images */ /* Acquire from MFW the amount of available images */
rc = qed_mcp_bist_nvm_test_get_num_images(p_hwfn, p_ptt, &num_images); rc = qed_mcp_bist_nvm_get_num_images(p_hwfn, p_ptt, &num_images);
if (rc || !num_images) { if (rc || !num_images) {
DP_ERR(p_hwfn, "Failed getting number of images\n"); DP_ERR(p_hwfn, "Failed getting number of images\n");
return -EINVAL; return -EINVAL;
...@@ -136,8 +136,8 @@ int qed_selftest_nvram(struct qed_dev *cdev) ...@@ -136,8 +136,8 @@ int qed_selftest_nvram(struct qed_dev *cdev)
/* This mailbox returns information about the image required for /* This mailbox returns information about the image required for
* reading it. * reading it.
*/ */
rc = qed_mcp_bist_nvm_test_get_image_att(p_hwfn, p_ptt, rc = qed_mcp_bist_nvm_get_image_att(p_hwfn, p_ptt,
&image_att, i); &image_att, i);
if (rc) { if (rc) {
DP_ERR(p_hwfn, DP_ERR(p_hwfn,
"Failed getting image index %d attributes\n", "Failed getting image index %d attributes\n",
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment