From: Nava kishore Manne <nava.manne@xxxxxxxxxx> Up on fpga configuration failure, the existing sysfs state interface is just providing the generic error message rather than providing the exact error code. This patch extends sysfs state interface to provide the exact error received from the lower layer along with the existing generic error message. Signed-off-by: Nava kishore Manne <nava.manne@xxxxxxxxxx> --- drivers/fpga/fpga-mgr.c | 20 +++++++++++++++++++- include/linux/fpga/fpga-mgr.h | 2 ++ 2 files changed, 21 insertions(+), 1 deletion(-) diff --git a/drivers/fpga/fpga-mgr.c b/drivers/fpga/fpga-mgr.c index 8efa67620e21..b2d74705a5a2 100644 --- a/drivers/fpga/fpga-mgr.c +++ b/drivers/fpga/fpga-mgr.c @@ -61,12 +61,14 @@ static inline int fpga_mgr_write_complete(struct fpga_manager *mgr, { int ret = 0; + mgr->err = 0; mgr->state = FPGA_MGR_STATE_WRITE_COMPLETE; if (mgr->mops->write_complete) ret = mgr->mops->write_complete(mgr, info); if (ret) { dev_err(&mgr->dev, "Error after writing image data to FPGA\n"); mgr->state = FPGA_MGR_STATE_WRITE_COMPLETE_ERR; + mgr->err = ret; return ret; } mgr->state = FPGA_MGR_STATE_OPERATING; @@ -154,6 +156,7 @@ static int fpga_mgr_parse_header_mapped(struct fpga_manager *mgr, { int ret; + mgr->err = 0; mgr->state = FPGA_MGR_STATE_PARSE_HEADER; ret = fpga_mgr_parse_header(mgr, info, buf, count); @@ -165,6 +168,7 @@ static int fpga_mgr_parse_header_mapped(struct fpga_manager *mgr, if (ret) { dev_err(&mgr->dev, "Error while parsing FPGA image header\n"); mgr->state = FPGA_MGR_STATE_PARSE_HEADER_ERR; + mgr->err = ret; } return ret; @@ -185,6 +189,7 @@ static int fpga_mgr_parse_header_sg_first(struct fpga_manager *mgr, int ret; mgr->state = FPGA_MGR_STATE_PARSE_HEADER; + mgr->err = 0; sg_miter_start(&miter, sgt->sgl, sgt->nents, SG_MITER_FROM_SG); if (sg_miter_next(&miter) && @@ -197,6 +202,7 @@ static int fpga_mgr_parse_header_sg_first(struct fpga_manager *mgr, if (ret && ret != -EAGAIN) { dev_err(&mgr->dev, "Error while parsing FPGA image header\n"); mgr->state = FPGA_MGR_STATE_PARSE_HEADER_ERR; + mgr->err = ret; } return ret; @@ -249,6 +255,7 @@ static void *fpga_mgr_parse_header_sg(struct fpga_manager *mgr, if (ret) { dev_err(&mgr->dev, "Error while parsing FPGA image header\n"); mgr->state = FPGA_MGR_STATE_PARSE_HEADER_ERR; + mgr->err = ret; kfree(buf); buf = ERR_PTR(ret); } @@ -272,6 +279,7 @@ static int fpga_mgr_write_init_buf(struct fpga_manager *mgr, size_t header_size = info->header_size; int ret; + mgr->err = 0; mgr->state = FPGA_MGR_STATE_WRITE_INIT; if (header_size > count) @@ -284,6 +292,7 @@ static int fpga_mgr_write_init_buf(struct fpga_manager *mgr, if (ret) { dev_err(&mgr->dev, "Error preparing FPGA for writing\n"); mgr->state = FPGA_MGR_STATE_WRITE_INIT_ERR; + mgr->err = ret; return ret; } @@ -370,6 +379,7 @@ static int fpga_mgr_buf_load_sg(struct fpga_manager *mgr, /* Write the FPGA image to the FPGA. */ mgr->state = FPGA_MGR_STATE_WRITE; + mgr->err = 0; if (mgr->mops->write_sg) { ret = fpga_mgr_write_sg(mgr, sgt); } else { @@ -405,6 +415,7 @@ static int fpga_mgr_buf_load_sg(struct fpga_manager *mgr, if (ret) { dev_err(&mgr->dev, "Error while writing image data to FPGA\n"); mgr->state = FPGA_MGR_STATE_WRITE_ERR; + mgr->err = ret; return ret; } @@ -437,10 +448,12 @@ static int fpga_mgr_buf_load_mapped(struct fpga_manager *mgr, * Write the FPGA image to the FPGA. */ mgr->state = FPGA_MGR_STATE_WRITE; + mgr->err = 0; ret = fpga_mgr_write(mgr, buf, count); if (ret) { dev_err(&mgr->dev, "Error while writing image data to FPGA\n"); mgr->state = FPGA_MGR_STATE_WRITE_ERR; + mgr->err = ret; return ret; } @@ -544,10 +557,11 @@ static int fpga_mgr_firmware_load(struct fpga_manager *mgr, dev_info(dev, "writing %s to %s\n", image_name, mgr->name); mgr->state = FPGA_MGR_STATE_FIRMWARE_REQ; - + mgr->err = 0; ret = request_firmware(&fw, image_name, dev); if (ret) { mgr->state = FPGA_MGR_STATE_FIRMWARE_REQ_ERR; + mgr->err = ret; dev_err(dev, "Error requesting firmware %s\n", image_name); return ret; } @@ -626,6 +640,10 @@ static ssize_t state_show(struct device *dev, { struct fpga_manager *mgr = to_fpga_manager(dev); + if (mgr->err) + return sprintf(buf, "%s: 0x%x\n", + state_str[mgr->state], mgr->err); + return sprintf(buf, "%s\n", state_str[mgr->state]); } diff --git a/include/linux/fpga/fpga-mgr.h b/include/linux/fpga/fpga-mgr.h index 54f63459efd6..be3a426ef903 100644 --- a/include/linux/fpga/fpga-mgr.h +++ b/include/linux/fpga/fpga-mgr.h @@ -202,6 +202,7 @@ struct fpga_manager_ops { * @compat_id: FPGA manager id for compatibility check. * @mops: pointer to struct of fpga manager ops * @priv: low level driver private date + * @err: low level driver error code */ struct fpga_manager { const char *name; @@ -211,6 +212,7 @@ struct fpga_manager { struct fpga_compat_id *compat_id; const struct fpga_manager_ops *mops; void *priv; + int err; }; #define to_fpga_manager(d) container_of(d, struct fpga_manager, dev) -- 2.25.1