From patchwork Tue Jan 11 17:26:00 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Beau Belgrave X-Patchwork-Id: 12710162 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id BB8F7C433EF for ; Tue, 11 Jan 2022 17:26:44 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1344229AbiAKR0n (ORCPT ); Tue, 11 Jan 2022 12:26:43 -0500 Received: from linux.microsoft.com ([13.77.154.182]:33946 "EHLO linux.microsoft.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1344085AbiAKR0f (ORCPT ); Tue, 11 Jan 2022 12:26:35 -0500 Received: from localhost.localdomain (c-73-140-2-214.hsd1.wa.comcast.net [73.140.2.214]) by linux.microsoft.com (Postfix) with ESMTPSA id BC03E20B718D; Tue, 11 Jan 2022 09:26:33 -0800 (PST) DKIM-Filter: OpenDKIM Filter v2.11.0 linux.microsoft.com BC03E20B718D DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linux.microsoft.com; s=default; t=1641921993; bh=4rS/OSFoB8cwnQ1Ju8K30aEaSCCMQ6qX3sGGO0R79Mc=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=e24buY60o/ZoxP541nZak7o3BbX+3e8wlOgcwOcIaArOLNJ9i0tgP3YbYL1jcHr+b uDvc0MnFli3GdNnTpCafIHldv4KAhL0FXy3Hm9YOjOzdrO4XVROpoouUvjeSv1JB2h +O0nvmMOZHR8JIi1sShE7Ld3+8s3NSf4zpJxmtfY= From: Beau Belgrave To: rostedt@goodmis.org, mhiramat@kernel.org Cc: linux-trace-devel@vger.kernel.org, linux-kernel@vger.kernel.org, beaub@linux.microsoft.com Subject: [PATCH v9 10/12] user_events: Add self-test for validator boundaries Date: Tue, 11 Jan 2022 09:26:00 -0800 Message-Id: <20220111172602.2513-11-beaub@linux.microsoft.com> X-Mailer: git-send-email 2.17.1 In-Reply-To: <20220111172602.2513-1-beaub@linux.microsoft.com> References: <20220111172602.2513-1-beaub@linux.microsoft.com> Precedence: bulk List-ID: X-Mailing-List: linux-trace-devel@vger.kernel.org Tests to ensure validator boundary cases are working correctly within close and far bounds. Ensures __data_loc and __rel_loc strings are null terminated and within range. Ensures min size checks work as expected. Signed-off-by: Beau Belgrave --- .../selftests/user_events/ftrace_test.c | 65 +++++++++++++++++++ 1 file changed, 65 insertions(+) diff --git a/tools/testing/selftests/user_events/ftrace_test.c b/tools/testing/selftests/user_events/ftrace_test.c index 68010fd7b719..a80fb5ef61d5 100644 --- a/tools/testing/selftests/user_events/ftrace_test.c +++ b/tools/testing/selftests/user_events/ftrace_test.c @@ -309,6 +309,71 @@ TEST_F(user, write_fault) { ASSERT_EQ(0, munmap(anon, l)); } +TEST_F(user, write_validator) { + struct user_reg reg = {0}; + struct iovec io[3]; + int loc, bytes; + char data[8]; + int before = 0, after = 0; + + reg.size = sizeof(reg); + reg.name_args = (__u64)"__test_event __rel_loc char[] data"; + + /* Register should work */ + ASSERT_EQ(0, ioctl(self->data_fd, DIAG_IOCSREG, ®)); + ASSERT_EQ(0, reg.write_index); + ASSERT_NE(0, reg.status_index); + + io[0].iov_base = ®.write_index; + io[0].iov_len = sizeof(reg.write_index); + io[1].iov_base = &loc; + io[1].iov_len = sizeof(loc); + io[2].iov_base = data; + bytes = snprintf(data, sizeof(data), "Test") + 1; + io[2].iov_len = bytes; + + /* Undersized write should fail */ + ASSERT_EQ(-1, writev(self->data_fd, (const struct iovec *)io, 1)); + ASSERT_EQ(EINVAL, errno); + + /* Enable event */ + self->enable_fd = open(enable_file, O_RDWR); + ASSERT_NE(-1, write(self->enable_fd, "1", sizeof("1"))) + + /* Full in-bounds write should work */ + before = trace_bytes(); + loc = DYN_LOC(0, bytes); + ASSERT_NE(-1, writev(self->data_fd, (const struct iovec *)io, 3)); + after = trace_bytes(); + ASSERT_GT(after, before); + + /* Out of bounds write should fault (offset way out) */ + loc = DYN_LOC(1024, bytes); + ASSERT_EQ(-1, writev(self->data_fd, (const struct iovec *)io, 3)); + ASSERT_EQ(EFAULT, errno); + + /* Out of bounds write should fault (offset 1 byte out) */ + loc = DYN_LOC(1, bytes); + ASSERT_EQ(-1, writev(self->data_fd, (const struct iovec *)io, 3)); + ASSERT_EQ(EFAULT, errno); + + /* Out of bounds write should fault (size way out) */ + loc = DYN_LOC(0, bytes + 1024); + ASSERT_EQ(-1, writev(self->data_fd, (const struct iovec *)io, 3)); + ASSERT_EQ(EFAULT, errno); + + /* Out of bounds write should fault (size 1 byte out) */ + loc = DYN_LOC(0, bytes + 1); + ASSERT_EQ(-1, writev(self->data_fd, (const struct iovec *)io, 3)); + ASSERT_EQ(EFAULT, errno); + + /* Non-Null should fault */ + memset(data, 'A', sizeof(data)); + loc = DYN_LOC(0, bytes); + ASSERT_EQ(-1, writev(self->data_fd, (const struct iovec *)io, 3)); + ASSERT_EQ(EFAULT, errno); +} + TEST_F(user, print_fmt) { int ret;