From patchwork Mon Mar 6 21:55:32 2017 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Kees Cook X-Patchwork-Id: 735968 Return-Path: X-Original-To: patchwork-incoming@ozlabs.org Delivered-To: patchwork-incoming@ozlabs.org Received: from lists.ozlabs.org (lists.ozlabs.org [103.22.144.68]) (using TLSv1.2 with cipher ADH-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id 3vcZ8r70KXz9sN9 for ; Tue, 7 Mar 2017 09:24:44 +1100 (AEDT) Authentication-Results: ozlabs.org; dkim=fail reason="signature verification failed" (1024-bit key; unprotected) header.d=chromium.org header.i=@chromium.org header.b="EWOGmgsY"; dkim-atps=neutral Received: from lists.ozlabs.org (lists.ozlabs.org [IPv6:2401:3900:2:1::3]) by lists.ozlabs.org (Postfix) with ESMTP id 3vcZ8r5yR4zDqfy for ; Tue, 7 Mar 2017 09:24:44 +1100 (AEDT) Authentication-Results: lists.ozlabs.org; dkim=fail reason="signature verification failed" (1024-bit key; unprotected) header.d=chromium.org header.i=@chromium.org header.b="EWOGmgsY"; dkim-atps=neutral X-Original-To: linuxppc-dev@lists.ozlabs.org Delivered-To: linuxppc-dev@lists.ozlabs.org Received: from mail-pf0-x22a.google.com (mail-pf0-x22a.google.com [IPv6:2607:f8b0:400e:c00::22a]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by lists.ozlabs.org (Postfix) with ESMTPS id 3vcYWP4Vk9zDqFh for ; Tue, 7 Mar 2017 08:55:45 +1100 (AEDT) Authentication-Results: lists.ozlabs.org; dkim=pass (1024-bit key; unprotected) header.d=chromium.org header.i=@chromium.org header.b="EWOGmgsY"; dkim-atps=neutral Received: by mail-pf0-x22a.google.com with SMTP id w189so65502690pfb.0 for ; Mon, 06 Mar 2017 13:55:45 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=chromium.org; s=google; h=from:to:cc:subject:date:message-id:in-reply-to:references; bh=lDjJJdO+GZNWXlPX+QLBHsy49T2G7sd6zfRXGjfyx5c=; b=EWOGmgsYV/TnsCbpnJNpgNwZ7sRzhMDNY4X88MHCupJIFkQ6UOndi2v2e9Xldn9C0j XR2mDeY0UIW+YypiPfJ2z2WLGeQD7VojP6FLMCZUiKxsAI8lVeq4kYHUmQlmVcIauQ9m uc4AuF7C484grjCfYkE2kF6J7PfK1B/O9ouqY= X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references; bh=lDjJJdO+GZNWXlPX+QLBHsy49T2G7sd6zfRXGjfyx5c=; b=Y46Uix/a3ih7nTGCeIcih/9eJp3MGBgQMScg1jepTTNxSZ4Niy1x9vOc29M3BEAKaF Uig6eMutUG9bkTEZE/+T6eEW8AW3JvWJ6ygGaAsguKbO68lC2Lo7yVP2dh702QMRr4oT F3tOHvLMkKwFuqoj+fIybJQ80SM5CZT5ZNegGyxTF/pmZ3eF+uAWUxfGYlooxLMDL5B0 ns2ilWnq4cpJlBrd+/ijCBoGb2mAaWr6xY/Nm/2m8OqpCPEOdPbhCKty1jMvF1fDrNbd AVkUSUuw2fPrVmzaAAFu7hHqCYx9l6RxAYb6BkafIH2ewX/vpf3CdFVv6eIZ8kfmw7ua zNpQ== X-Gm-Message-State: AMke39lOQn1aqW7Ar1iSTZmrQOo60WKjspPwQuv8OLmdJr1jmArNsp+RWm9b/t1VvJLz2/Dl X-Received: by 10.99.171.5 with SMTP id p5mr22897970pgf.182.1488837343882; Mon, 06 Mar 2017 13:55:43 -0800 (PST) Received: from www.outflux.net ([2002:ada4:7085:0:205a:2b55:4e6d:7d63]) by smtp.gmail.com with ESMTPSA id 80sm202058pfy.67.2017.03.06.13.55.41 (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Mon, 06 Mar 2017 13:55:43 -0800 (PST) From: Kees Cook To: linux-kernel@vger.kernel.org Subject: [PATCH 18/18] pstore: Remove write_buf() callback Date: Mon, 6 Mar 2017 13:55:32 -0800 Message-Id: <1488837332-71582-19-git-send-email-keescook@chromium.org> X-Mailer: git-send-email 2.7.4 In-Reply-To: <1488837332-71582-1-git-send-email-keescook@chromium.org> References: <1488837332-71582-1-git-send-email-keescook@chromium.org> X-BeenThere: linuxppc-dev@lists.ozlabs.org X-Mailman-Version: 2.1.23 Precedence: list List-Id: Linux on PowerPC Developers Mail List List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: linux-efi@vger.kernel.org, linux-doc@vger.kernel.org, Matt Fleming , Pan Xinhui , Paul Gortmaker , Paul Mackerras , Anton Vorontsov , linux-acpi@vger.kernel.org, Nathan Fontenot , Len Brown , Kees Cook , Nobuhiro Iwamatsu , Geliang Tang , Tony Luck , Daniel Axtens , Qiuxu Zhuo , Ard Biesheuvel , "Rafael J. Wysocki" , Colin Cross , linuxppc-dev@lists.ozlabs.org Errors-To: linuxppc-dev-bounces+patchwork-incoming=ozlabs.org@lists.ozlabs.org Sender: "Linuxppc-dev" Now that write() and write_buf() are functionally identical, this removes write_buf(), and renames write_buf_user() to write_user(). Additionally adds sanity-checks for pstore_info's declared functions and flags at registration time. Signed-off-by: Kees Cook --- fs/pstore/ftrace.c | 4 ++-- fs/pstore/platform.c | 35 ++++++++++++++++++++--------------- fs/pstore/pmsg.c | 4 ++-- fs/pstore/ram.c | 10 +++++----- include/linux/pstore.h | 29 ++++++++++------------------- 5 files changed, 39 insertions(+), 43 deletions(-) diff --git a/fs/pstore/ftrace.c b/fs/pstore/ftrace.c index a5506ec6995e..06aab07b6bb7 100644 --- a/fs/pstore/ftrace.c +++ b/fs/pstore/ftrace.c @@ -53,7 +53,7 @@ static void notrace pstore_ftrace_call(unsigned long ip, rec.parent_ip = parent_ip; pstore_ftrace_write_timestamp(&rec, pstore_ftrace_stamp++); pstore_ftrace_encode_cpu(&rec, raw_smp_processor_id()); - psinfo->write_buf(&record); + psinfo->write(&record); local_irq_restore(flags); } @@ -122,7 +122,7 @@ void pstore_register_ftrace(void) { struct dentry *file; - if (!psinfo->write_buf) + if (!psinfo->write) return; pstore_ftrace_dir = debugfs_create_dir("pstore", NULL); diff --git a/fs/pstore/platform.c b/fs/pstore/platform.c index 1e6642a2063e..e79f170fa79b 100644 --- a/fs/pstore/platform.c +++ b/fs/pstore/platform.c @@ -604,7 +604,7 @@ static void pstore_console_write(struct console *con, const char *s, unsigned c) } record.buf = (char *)s; record.size = c; - psinfo->write_buf(&record); + psinfo->write(&record); spin_unlock_irqrestore(&psinfo->buf_lock, flags); s += c; c = e - s; @@ -632,15 +632,8 @@ static void pstore_register_console(void) {} static void pstore_unregister_console(void) {} #endif -static int pstore_write_compat(struct pstore_record *record) -{ - record->buf = psinfo->buf; - - return record->psi->write_buf(record); -} - -static int pstore_write_buf_user_compat(struct pstore_record *record, - const char __user *buf) +static int pstore_write_user_compat(struct pstore_record *record, + const char __user *buf) { unsigned long flags = 0; size_t i, bufsize, total_size = record->size; @@ -662,7 +655,7 @@ static int pstore_write_buf_user_compat(struct pstore_record *record, break; } record->size = c; - ret = record->psi->write_buf(record); + ret = record->psi->write(record); if (unlikely(ret < 0)) break; i += c; @@ -687,6 +680,20 @@ int pstore_register(struct pstore_info *psi) return -EPERM; } + /* Sanity check flags. */ + if (!psi->flags) { + pr_warn("backend '%s' must support at least one frontend\n", + psi->name); + return -EINVAL; + } + + /* Check for required functions. */ + if (!psi->read || !psi->write) { + pr_warn("backend '%s' must implement read() and write()\n", + psi->name); + return -EINVAL; + } + spin_lock(&pstore_lock); if (psinfo) { pr_warn("backend '%s' already loaded: ignoring '%s'\n", @@ -695,10 +702,8 @@ int pstore_register(struct pstore_info *psi) return -EBUSY; } - if (!psi->write) - psi->write = pstore_write_compat; - if (!psi->write_buf_user) - psi->write_buf_user = pstore_write_buf_user_compat; + if (!psi->write_user) + psi->write_user = pstore_write_user_compat; psinfo = psi; mutex_init(&psinfo->read_mutex); spin_unlock(&pstore_lock); diff --git a/fs/pstore/pmsg.c b/fs/pstore/pmsg.c index ce35907602de..c16a2477e106 100644 --- a/fs/pstore/pmsg.c +++ b/fs/pstore/pmsg.c @@ -33,12 +33,12 @@ static ssize_t write_pmsg(struct file *file, const char __user *buf, if (!count) return 0; - /* check outside lock, page in any data. write_buf_user also checks */ + /* check outside lock, page in any data. write_user also checks */ if (!access_ok(VERIFY_READ, buf, count)) return -EFAULT; mutex_lock(&pmsg_lock); - ret = psinfo->write_buf_user(&record, buf); + ret = psinfo->write_user(&record, buf); mutex_unlock(&pmsg_lock); return ret ? ret : count; } diff --git a/fs/pstore/ram.c b/fs/pstore/ram.c index d85e1adae1b6..5523df7f17ef 100644 --- a/fs/pstore/ram.c +++ b/fs/pstore/ram.c @@ -378,7 +378,7 @@ static size_t ramoops_write_kmsg_hdr(struct persistent_ram_zone *prz, return len; } -static int notrace ramoops_pstore_write_buf(struct pstore_record *record) +static int notrace ramoops_pstore_write(struct pstore_record *record) { struct ramoops_context *cxt = record->psi->data; struct persistent_ram_zone *prz; @@ -451,8 +451,8 @@ static int notrace ramoops_pstore_write_buf(struct pstore_record *record) return 0; } -static int notrace ramoops_pstore_write_buf_user(struct pstore_record *record, - const char __user *buf) +static int notrace ramoops_pstore_write_user(struct pstore_record *record, + const char __user *buf) { if (record->type == PSTORE_TYPE_PMSG) { struct ramoops_context *cxt = record->psi->data; @@ -503,8 +503,8 @@ static struct ramoops_context oops_cxt = { .name = "ramoops", .open = ramoops_pstore_open, .read = ramoops_pstore_read, - .write_buf = ramoops_pstore_write_buf, - .write_buf_user = ramoops_pstore_write_buf_user, + .write = ramoops_pstore_write, + .write_user = ramoops_pstore_write_user, .erase = ramoops_pstore_erase, }, }; diff --git a/include/linux/pstore.h b/include/linux/pstore.h index 7f6eaa71504e..936744221171 100644 --- a/include/linux/pstore.h +++ b/include/linux/pstore.h @@ -130,27 +130,19 @@ struct pstore_record { * available, or negative on error. * * @write: - * Perform a frontend notification of a write to a backend record. The - * data to be stored has already been written to the registered @buf - * of the @psi structure. + * A newly generated record needs to be written to backend storage. * * @record: - * pointer to record metadata. Note that @buf is NULL, since - * the @buf registered with @psi is what has been written. The - * backend is expected to update @id. + * pointer to record metadata. When @type is PSTORE_TYPE_DMESG, + * @buf will be pointing to the preallocated @psi.buf, since + * memory allocation may be broken during an Oops. Regardless, + * @buf must be proccesed or copied before returning. The + * backend is also expected to write @id with something that + 8 can help identify this record to a future @erase callback. * * Returns 0 on success, and non-zero on error. * - * @write_buf: - * Perform a frontend write to a backend record. The record contains - * all metadata and the buffer to write to backend storage. (Unlike - * @write, this does not use the @psi @buf.) - * - * @record: pointer to record metadata. - * - * Returns 0 on success, and non-zero on error. - * - * @write_buf_user: + * @write_user: * Perform a frontend write to a backend record, using a specified * buffer that is coming directly from userspace, instead of the * @record @buf. @@ -188,9 +180,8 @@ struct pstore_info { int (*close)(struct pstore_info *psi); ssize_t (*read)(struct pstore_record *record); int (*write)(struct pstore_record *record); - int (*write_buf)(struct pstore_record *record); - int (*write_buf_user)(struct pstore_record *record, - const char __user *buf); + int (*write_user)(struct pstore_record *record, + const char __user *buf); int (*erase)(struct pstore_record *record); };