[Skiboot] [PATCH V2 20/21] core/pldm: Add file io write request

Christophe Lombard clombard at linux.vnet.ibm.com
Fri Mar 18 21:53:59 AEDT 2022


Le 16/03/2022 à 10:14, Abhishek SIngh Tomar a écrit :
> Hello Christophe
>
> In function write_file_req(uint32_t file_handle, uint32_t file_length,
> void *buf, uint32_t offset, uint64_t size)
>> +	if ((!size) || (size > file_length))
>> +		return OPAL_PARAMETER;
> I am Unable to understand why file length need to be > size in case of
> write.
A bad copy/paste from read_file_re().
Thanks.
>
> Regards
> Abhishek Singh Tomar
>
> On Fri, Mar 04, 2022 at 02:11:53PM +0100, Christophe Lombard wrote:
>> Send/receive a PLDM WriteFile request message.
>>
>> Due to maximum transfer size for PLDM protocol, we have to send several
>> write requests, if necessary.
>>
>> Signed-off-by: Christophe Lombard <clombard at linux.vnet.ibm.com>
>> ---
>>   core/pldm/pldm-file-io-requests.c | 130 ++++++++++++++++++++++++++++++
>>   core/pldm/pldm.h                  |   4 +
>>   2 files changed, 134 insertions(+)
>>
>> diff --git a/core/pldm/pldm-file-io-requests.c b/core/pldm/pldm-file-io-requests.c
>> index ce4297d0..a86527c0 100644
>> --- a/core/pldm/pldm-file-io-requests.c
>> +++ b/core/pldm/pldm-file-io-requests.c
>> @@ -163,6 +163,136 @@ int pldm_file_io_read_file(uint32_t file_handle,
>>   			     buf, offset, size);
>>   }
>>   
>> +/*
>> + * Send/receive a PLDM WriteFile request message.
>> + */
>> +static int write_file_req(uint32_t file_handle, uint32_t file_length,
>> +			  void *buf, uint32_t offset, uint64_t size)
>> +{
>> +	void *response_msg, *current_ptr, *payload_data;
>> +	uint32_t total_write, resp_length, request_length;
>> +	size_t response_len, payload_len;
>> +	uint8_t completion_code;
>> +	int num_transfers;
>> +	char *request_msg;
>> +	int rc, i;
>> +
>> +	struct pldm_write_file_req file_req = {
>> +		.file_handle = file_handle,
>> +		.offset = offset,
>> +		.length = size
>> +	};
>> +
>> +	if (!file_length)
>> +		return OPAL_PARAMETER;
>> +
>> +	if ((!size) || (size > file_length))
>> +		return OPAL_PARAMETER;
>> +
>> +	if ((offset) && (offset > file_length))
>> +		return OPAL_PARAMETER;
>> +
>> +	request_length = sizeof(struct pldm_msg_hdr) +
>> +			 sizeof(struct pldm_write_file_req) +
>> +			 size;
>> +	request_msg = malloc(request_length);
>> +
>> +	payload_data = ((struct pldm_msg *)request_msg)->payload
>> +			+ sizeof(file_req.file_handle)
>> +			+ sizeof(file_req.offset)
>> +			+ sizeof(file_req.length);
>> +	memcpy(payload_data, buf, size);
>> +	current_ptr = payload_data;
>> +	num_transfers = 1;
>> +	total_write = 0;
>> +
>> +	if (size > MAX_TRANSFER_SIZE_BYTES) {
>> +		num_transfers = (size + MAX_TRANSFER_SIZE_BYTES - 1) /
>> +				MAX_TRANSFER_SIZE_BYTES;
>> +		file_req.length = MAX_TRANSFER_SIZE_BYTES;
>> +	}
>> +
>> +	prlog(PR_TRACE, "%s - file_handle: %d, offset: 0x%x, size: 0x%x, num_transfers: %d\n",
>> +			__func__, file_handle, file_req.offset,
>> +			file_req.length, num_transfers);
>> +
>> +	for (i = 0; i < num_transfers; i++) {
>> +		file_req.offset = offset + (i * MAX_TRANSFER_SIZE_BYTES);
>> +
>> +		/* Encode the file request */
>> +		rc = encode_write_file_req(
>> +				DEFAULT_INSTANCE_ID,
>> +				file_req.file_handle,
>> +				file_req.offset,
>> +				file_req.length,
>> +				(struct pldm_msg *)request_msg);
>> +		if (rc != PLDM_SUCCESS) {
>> +			prlog(PR_ERR, "Encode WriteFileReq Error (rc: %d)\n",
>> +				      rc);
>> +			free(request_msg);
>> +			return OPAL_PARAMETER;
>> +		}
>> +
>> +		/* Send and get the response message bytes */
>> +		rc = pldm_do_request(BMC_EID, request_msg,
>> +				     request_length - 1,
>> +				     &response_msg, &response_len);
>> +		if (rc) {
>> +			prlog(PR_ERR, "PLDM: Communication Error (req:"
>> +				      "WriteFileReq, rc: %d)\n", rc);
>> +			free(request_msg);
>> +			return OPAL_PARAMETER;
>> +		}
>> +
>> +		/* Decode the message */
>> +		payload_len = response_len - sizeof(struct pldm_msg_hdr);
>> +		rc = decode_write_file_resp(
>> +				response_msg,
>> +				payload_len,
>> +				&completion_code,
>> +				&resp_length);
>> +		if (rc != PLDM_SUCCESS || completion_code != PLDM_SUCCESS) {
>> +			prlog(PR_ERR, "Decode WriteFileResp Error (rc: %d, cc: %d)\n",
>> +				      rc, completion_code);
>> +			free(request_msg);
>> +			return OPAL_PARAMETER;
>> +		}
>> +
>> +		if (resp_length == 0) {
>> +			free(response_msg);
>> +			break;
>> +		}
>> +
>> +		total_write += resp_length;
>> +		current_ptr += resp_length;
>> +		free(response_msg);
>> +
>> +		if (total_write == size)
>> +			break;
>> +		else if (resp_length != file_req.length) {
>> +			/* end of file */
>> +			break;
>> +		} else if (MAX_TRANSFER_SIZE_BYTES > (size - total_write))
>> +			file_req.length = size - total_write;
>> +	}
>> +
>> +	free(request_msg);
>> +
>> +	return OPAL_SUCCESS;
>> +}
>> +
>> +int pldm_file_io_write_file(uint32_t file_handle,
>> +			    uint32_t file_length,
>> +			    void *buf, uint32_t offset,
>> +			    uint64_t size)
>> +{
>> +	if (!file_io_ready)
>> +		return OPAL_PARAMETER;
>> +
>> +	return write_file_req(file_handle, file_length,
>> +			      buf, offset, size);
>> +}
>> +
>>   /*
>>    * Send/receive a PLDM GetFileTable request message.
>>    * The file table contains the list of files available and
>> diff --git a/core/pldm/pldm.h b/core/pldm/pldm.h
>> index da572a6a..e7a175f5 100644
>> --- a/core/pldm/pldm.h
>> +++ b/core/pldm/pldm.h
>> @@ -55,6 +55,10 @@ int pldm_file_io_read_file(uint32_t file_handle,
>>   			   uint32_t file_length,
>>   			   void *buf, uint32_t offset,
>>   			   uint64_t size);
>> +int pldm_file_io_write_file(uint32_t file_handle,
>> +			    uint32_t file_length,
>> +			    void *buf, uint32_t offset,
>> +			    uint64_t size);
>>   int pldm_file_io_init(void);
>>   
>>   int pldm_fru_get_record_by_option(uint16_t fru_table_handle,
>> -- 
>> 2.35.1
>>
>> _______________________________________________
>> Skiboot mailing list
>> Skiboot at lists.ozlabs.org
>> https://lists.ozlabs.org/listinfo/skiboot



More information about the Skiboot mailing list