From cb0c2a7430788b4cd13d303a02a021bb53e3db4b Mon Sep 17 00:00:00 2001 From: Heinrich Schuchardt Date: Sat, 6 Apr 2019 16:27:34 +0200 Subject: [PATCH] efi_loader: correct file creation The EFI shell expects that after opening a file with EFI_FILE_MODE_CREATE GetInfo() succeeds. Up to now we do not actually create the file when method Open() of the EFI_FILE_PROTOCOL is called. If method Open() of the EFI_FILE_PROTOCOL is called with EFI_FILE_MODE_CREATE and the file does not yet exist, call fs_write() with a buffer size of zero to actually create the file. Signed-off-by: Heinrich Schuchardt --- lib/efi_loader/efi_file.c | 35 +++++++++++++++++++++++++++-------- 1 file changed, 27 insertions(+), 8 deletions(-) diff --git a/lib/efi_loader/efi_file.c b/lib/efi_loader/efi_file.c index be3e55f4d8..e7ea2466fe 100644 --- a/lib/efi_loader/efi_file.c +++ b/lib/efi_loader/efi_file.c @@ -134,6 +134,25 @@ static int sanitize_path(char *path) return 0; } +/** + * efi_create_file() - create file or directory + * + * @fh: file handle + * @attributes: attributes for newly created file + * Returns: 0 for success + */ +static int efi_create_file(struct file_handle *fh, u64 attributes) +{ + loff_t actwrite; + void *buffer = &actwrite; + + if (attributes & EFI_FILE_DIRECTORY) + return fs_mkdir(fh->path); + else + return fs_write(fh->path, map_to_sysmem(buffer), 0, 0, + &actwrite); +} + /** * file_open() - open a file handle * @@ -176,6 +195,7 @@ static struct efi_file_handle *file_open(struct file_system *fs, if (parent) { char *p = fh->path; + int exists; if (plen > 0) { strcpy(p, parent->path); @@ -192,18 +212,17 @@ static struct efi_file_handle *file_open(struct file_system *fs, if (set_blk_dev(fh)) goto error; - if ((mode & EFI_FILE_MODE_CREATE) && - (attributes & EFI_FILE_DIRECTORY)) { - if (fs_mkdir(fh->path)) - goto error; - } else if (!((mode & EFI_FILE_MODE_CREATE) || - fs_exists(fh->path))) - goto error; - + exists = fs_exists(fh->path); /* fs_exists() calls fs_close(), so open file system again */ if (set_blk_dev(fh)) goto error; + if (!exists) { + if (!(mode & EFI_FILE_MODE_CREATE) || + efi_create_file(fh, attributes)) + goto error; + } + /* figure out if file is a directory: */ fh->isdir = is_dir(fh); } else { -- 2.25.1