Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: GPL-2.0-only
0002 /*
0003  * Copyright (C) 2020-2021 Intel Corporation.
0004  */
0005 
0006 #include "iosm_ipc_coredump.h"
0007 
0008 /**
0009  * ipc_coredump_collect - To collect coredump
0010  * @devlink:            Pointer to devlink instance.
0011  * @data:               Pointer to snapshot
0012  * @entry:              ID of requested snapshot
0013  * @region_size:        Region size
0014  *
0015  * Returns: 0 on success, error on failure
0016  */
0017 int ipc_coredump_collect(struct iosm_devlink *devlink, u8 **data, int entry,
0018              u32 region_size)
0019 {
0020     int ret, bytes_to_read, bytes_read = 0, i = 0;
0021     s32 remaining;
0022     u8 *data_ptr;
0023 
0024     data_ptr = vmalloc(region_size);
0025     if (!data_ptr)
0026         return -ENOMEM;
0027 
0028     remaining = devlink->cd_file_info[entry].actual_size;
0029     ret = ipc_devlink_send_cmd(devlink, rpsi_cmd_coredump_get, entry);
0030     if (ret) {
0031         dev_err(devlink->dev, "Send coredump_get cmd failed");
0032         goto get_cd_fail;
0033     }
0034     while (remaining > 0) {
0035         bytes_to_read = min(remaining, MAX_DATA_SIZE);
0036         bytes_read = 0;
0037         ret = ipc_imem_sys_devlink_read(devlink, data_ptr + i,
0038                         bytes_to_read, &bytes_read);
0039         if (ret) {
0040             dev_err(devlink->dev, "CD data read failed");
0041             goto get_cd_fail;
0042         }
0043         remaining -= bytes_read;
0044         i += bytes_read;
0045     }
0046 
0047     *data = data_ptr;
0048 
0049     return 0;
0050 
0051 get_cd_fail:
0052     vfree(data_ptr);
0053     return ret;
0054 }
0055 
0056 /**
0057  * ipc_coredump_get_list - Get coredump list from modem
0058  * @devlink:         Pointer to devlink instance.
0059  * @cmd:             RPSI command to be sent
0060  *
0061  * Returns: 0 on success, error on failure
0062  */
0063 int ipc_coredump_get_list(struct iosm_devlink *devlink, u16 cmd)
0064 {
0065     u32 byte_read, num_entries, file_size;
0066     struct iosm_cd_table *cd_table;
0067     u8 size[MAX_SIZE_LEN], i;
0068     char *filename;
0069     int ret;
0070 
0071     cd_table = kzalloc(MAX_CD_LIST_SIZE, GFP_KERNEL);
0072     if (!cd_table) {
0073         ret = -ENOMEM;
0074         goto  cd_init_fail;
0075     }
0076 
0077     ret = ipc_devlink_send_cmd(devlink, cmd, MAX_CD_LIST_SIZE);
0078     if (ret) {
0079         dev_err(devlink->dev, "rpsi_cmd_coredump_start failed");
0080         goto cd_init_fail;
0081     }
0082 
0083     ret = ipc_imem_sys_devlink_read(devlink, (u8 *)cd_table,
0084                     MAX_CD_LIST_SIZE, &byte_read);
0085     if (ret) {
0086         dev_err(devlink->dev, "Coredump data is invalid");
0087         goto cd_init_fail;
0088     }
0089 
0090     if (byte_read != MAX_CD_LIST_SIZE)
0091         goto cd_init_fail;
0092 
0093     if (cmd == rpsi_cmd_coredump_start) {
0094         num_entries = le32_to_cpu(cd_table->list.num_entries);
0095         if (num_entries == 0 || num_entries > IOSM_NOF_CD_REGION) {
0096             ret = -EINVAL;
0097             goto cd_init_fail;
0098         }
0099 
0100         for (i = 0; i < num_entries; i++) {
0101             file_size = le32_to_cpu(cd_table->list.entry[i].size);
0102             filename = cd_table->list.entry[i].filename;
0103 
0104             if (file_size > devlink->cd_file_info[i].default_size) {
0105                 ret = -EINVAL;
0106                 goto cd_init_fail;
0107             }
0108 
0109             devlink->cd_file_info[i].actual_size = file_size;
0110             dev_dbg(devlink->dev, "file: %s actual size %d",
0111                 filename, file_size);
0112             devlink_flash_update_status_notify(devlink->devlink_ctx,
0113                                filename,
0114                                "FILENAME", 0, 0);
0115             snprintf(size, sizeof(size), "%d", file_size);
0116             devlink_flash_update_status_notify(devlink->devlink_ctx,
0117                                size, "FILE SIZE",
0118                                0, 0);
0119         }
0120     }
0121 
0122 cd_init_fail:
0123     kfree(cd_table);
0124     return ret;
0125 }