From patchwork Mon May 7 21:01:31 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Johannes Weiner X-Patchwork-Id: 10384785 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork.web.codeaurora.org (Postfix) with ESMTP id 5F55E60353 for ; Mon, 7 May 2018 21:00:10 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 3BEA728B24 for ; Mon, 7 May 2018 21:00:10 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 3097528B4A; Mon, 7 May 2018 21:00:10 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-2.8 required=2.0 tests=BAYES_00,DKIM_SIGNED, MAILING_LIST_MULTI,RCVD_IN_DNSWL_NONE,T_DKIM_INVALID autolearn=ham version=3.3.1 Received: from kanga.kvack.org (kanga.kvack.org [205.233.56.17]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 608EE28B24 for ; Mon, 7 May 2018 21:00:09 +0000 (UTC) Received: by kanga.kvack.org (Postfix) id 03DAA6B026C; Mon, 7 May 2018 17:00:07 -0400 (EDT) Delivered-To: linux-mm-outgoing@kvack.org Received: by kanga.kvack.org (Postfix, from userid 40) id 0157E6B026D; Mon, 7 May 2018 17:00:06 -0400 (EDT) X-Original-To: int-list-linux-mm@kvack.org X-Delivered-To: int-list-linux-mm@kvack.org Received: by kanga.kvack.org (Postfix, from userid 63042) id E71A06B026E; Mon, 7 May 2018 17:00:06 -0400 (EDT) X-Original-To: linux-mm@kvack.org X-Delivered-To: linux-mm@kvack.org Received: from mail-wm0-f70.google.com (mail-wm0-f70.google.com [74.125.82.70]) by kanga.kvack.org (Postfix) with ESMTP id 875966B026C for ; Mon, 7 May 2018 17:00:06 -0400 (EDT) Received: by mail-wm0-f70.google.com with SMTP id e74so2580187wmg.5 for ; Mon, 07 May 2018 14:00:06 -0700 (PDT) X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:dkim-signature:from:to:cc:subject:date :message-id:in-reply-to:references; bh=1iClfn4HlKN+hDTHHl595345vpFkPY3xJZGmTVC9G8E=; b=VGyjE5g+RaPgaPDnVAylF5nxpqaMTc6EFd4mm7mnEuBjE37Lb+QxK7SNGFJy0l/zyg N/2KDphYa9h9c0x7ryBdO62n/a1uf2w015DXA5tataRE3TPxNy6Z427KE3k/06rxcIVM YKUKTvBtfO/wRVRWaDGmMM9tW5NF1s/SrG8hCUocbb/AmxyrTsPxZCBVojdD21zaYBvc FZ1idw51RCcfGUaVFqsjcNW0L9cClFFmJiOhfW5f5n9gB3IsxdObMW+9eGRxNLPriEWp vYoyBTJbDHitpdy2W10nwURJZPn4ws4gzQn7I+XEL/agxI2tGY8fzfNDd5Oox0v8/RKE Pw8w== X-Gm-Message-State: ALQs6tCg1Vz7BEzH9J8/3RD3aqcAHLAyPns5Lg0+pOwjiyyNxY0O9Prm GoVQ4k7d3RboXAb2cdRUozx2s9YlCwuQcJQ+LOXwoxh+LPkhaYlCqw/am4ZWNACElre70wLps3U BwP8t5xOyFgDnuELmSq6Gv6EkfTdPPnvXH/79ot8SBbF5ogFcNW0rTV0xo23yJQAxcg== X-Received: by 2002:a50:9dc8:: with SMTP id l8-v6mr28993212edk.234.1525726806058; Mon, 07 May 2018 14:00:06 -0700 (PDT) X-Google-Smtp-Source: AB8JxZpI4ejH9spVPHPPzgNXdgighCybeNMz1xDiClLhrPS7+HPmf5+qOqbdAU+r7Kp4Dpk0S6Sl X-Received: by 2002:a50:9dc8:: with SMTP id l8-v6mr28993160edk.234.1525726805191; Mon, 07 May 2018 14:00:05 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1525726805; cv=none; d=google.com; s=arc-20160816; b=jHFfHcCeFXnsIVhOJs3xVic/BP/+/eFJB+3+zc8ogT9qzqpTJgW4Cs7Lbj9zjKnYIX 7iS4APg0lzPQWpsXYZpyEbB87D1nH8dolmBBGHhx5sgCCO8jWo0DuslhR51hPaJsV4hL G4AyeOUpjWFXQcoBfhumf8Prp38WCv3KW+Fokyc7idc03vF58+PI85eZgdgWLxba0RVL 1bvigkGbYCqWAp0niN5QQGwr0nVowDRkBew58TMOxkMEyBtNzIgxIGgNj/ygIyXGr4+D 8vA6BgV2palAh+kpV5PTdbThR0LH8wjeXiCft9twa5RKSNjbFXECoNeISg2uT7O7uU9s Oi+w== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=references:in-reply-to:message-id:date:subject:cc:to:from :dkim-signature:arc-authentication-results; bh=1iClfn4HlKN+hDTHHl595345vpFkPY3xJZGmTVC9G8E=; b=dJRO6QEdzjrUPg7exJFnGrjw57JVV2yQpkJVm600DE1lwoZ364hTGW0gasTeGZs8AB Wgy8ygOSLCqC5uE6L7Ey14nKE83S/u6fvadfVJ42zi25oDat2IUroZTA7C4Zx7ROfC7S befULVuUsCfcaIi3+HMwsNF7SQdRCH4rsj+DOtX6iZaUDxRLkDfNoEp4D3wfRoF/9aGR vXsQX5VmoJcsSft2Cr4J7YbG9+upnvt02ifZxHg4gjEbB9DahclanI454HrHsgcKePgo WUzai0Qh4SZQNRO5AgG9zwdAJbUybeV5DobVVIAv96GtTExobMPCNtV4JWI60NXATDhd Mf2g== ARC-Authentication-Results: i=1; mx.google.com; dkim=pass header.i=@cmpxchg.org header.s=x header.b=pOCOWEF9; spf=pass (google.com: domain of hannes@cmpxchg.org designates 85.214.110.215 as permitted sender) smtp.mailfrom=hannes@cmpxchg.org; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=cmpxchg.org Received: from gum.cmpxchg.org (gum.cmpxchg.org. [85.214.110.215]) by mx.google.com with ESMTPS id l57-v6si5294079edb.393.2018.05.07.14.00.05 for (version=TLS1_2 cipher=ECDHE-RSA-CHACHA20-POLY1305 bits=256/256); Mon, 07 May 2018 14:00:05 -0700 (PDT) Received-SPF: pass (google.com: domain of hannes@cmpxchg.org designates 85.214.110.215 as permitted sender) client-ip=85.214.110.215; Authentication-Results: mx.google.com; dkim=pass header.i=@cmpxchg.org header.s=x header.b=pOCOWEF9; spf=pass (google.com: domain of hannes@cmpxchg.org designates 85.214.110.215 as permitted sender) smtp.mailfrom=hannes@cmpxchg.org; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=cmpxchg.org DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=cmpxchg.org ; s=x; h=References:In-Reply-To:Message-Id:Date:Subject:Cc:To:From:Sender: Reply-To:MIME-Version:Content-Type:Content-Transfer-Encoding:Content-ID: Content-Description:Resent-Date:Resent-From:Resent-Sender:Resent-To:Resent-Cc :Resent-Message-ID:List-Id:List-Help:List-Unsubscribe:List-Subscribe: List-Post:List-Owner:List-Archive; bh=1iClfn4HlKN+hDTHHl595345vpFkPY3xJZGmTVC9G8E=; b=pOCOWEF984Q7MoQVXe88i1yF0t rqioncROWo0lVScdiUVVcoOT28O8FjTXxB8H4sL6mklrEnhsgRBs9S40vnDPAlRZ1aZrQjRQzfqaH j3hxdg8RK/1tsVipKRtAcwFs5vz+aHmGjqOxoBtVNOL/QbuNt5x50p7zaTguzU1BsPuE=; From: Johannes Weiner To: linux-kernel@vger.kernel.org, linux-mm@kvack.org, linux-block@vger.kernel.org, cgroups@vger.kernel.org Cc: Ingo Molnar , Peter Zijlstra , Andrew Morton , Tejun Heo , Balbir Singh , Mike Galbraith , Oliver Yang , Shakeel Butt , xxx xxx , Taras Kondratiuk , Daniel Walker , Vinayak Menon , Ruslan Ruslichenko , kernel-team@fb.com Subject: [PATCH 3/7] delayacct: track delays from thrashing cache pages Date: Mon, 7 May 2018 17:01:31 -0400 Message-Id: <20180507210135.1823-4-hannes@cmpxchg.org> X-Mailer: git-send-email 2.17.0 In-Reply-To: <20180507210135.1823-1-hannes@cmpxchg.org> References: <20180507210135.1823-1-hannes@cmpxchg.org> X-Bogosity: Ham, tests=bogofilter, spamicity=0.000000, version=1.2.4 Sender: owner-linux-mm@kvack.org Precedence: bulk X-Loop: owner-majordomo@kvack.org List-ID: X-Virus-Scanned: ClamAV using ClamSMTP Delay accounting already measures the time a task spends in direct reclaim and waiting for swapin, but in low memory situations tasks spend can spend a significant amount of their time waiting on thrashing page cache. This isn't tracked right now. To know the full impact of memory contention on an individual task, measure the delay when waiting for a recently evicted active cache page to read back into memory. Also update tools/accounting/getdelays.c: [hannes@computer accounting]$ sudo ./getdelays -d -p 1 print delayacct stats ON PID 1 CPU count real total virtual total delay total delay average 50318 745000000 847346785 400533713 0.008ms IO count delay total delay average 435 122601218 0ms SWAP count delay total delay average 0 0 0ms RECLAIM count delay total delay average 0 0 0ms THRASHING count delay total delay average 19 12621439 0ms Signed-off-by: Johannes Weiner --- include/linux/delayacct.h | 23 +++++++++++++++++++++++ include/uapi/linux/taskstats.h | 6 +++++- kernel/delayacct.c | 15 +++++++++++++++ mm/filemap.c | 11 +++++++++++ tools/accounting/getdelays.c | 8 +++++++- 5 files changed, 61 insertions(+), 2 deletions(-) diff --git a/include/linux/delayacct.h b/include/linux/delayacct.h index 5e335b6203f4..d3e75b3ba487 100644 --- a/include/linux/delayacct.h +++ b/include/linux/delayacct.h @@ -57,7 +57,12 @@ struct task_delay_info { u64 freepages_start; u64 freepages_delay; /* wait for memory reclaim */ + + u64 thrashing_start; + u64 thrashing_delay; /* wait for thrashing page */ + u32 freepages_count; /* total count of memory reclaim */ + u32 thrashing_count; /* total count of thrash waits */ }; #endif @@ -76,6 +81,8 @@ extern int __delayacct_add_tsk(struct taskstats *, struct task_struct *); extern __u64 __delayacct_blkio_ticks(struct task_struct *); extern void __delayacct_freepages_start(void); extern void __delayacct_freepages_end(void); +extern void __delayacct_thrashing_start(void); +extern void __delayacct_thrashing_end(void); static inline int delayacct_is_task_waiting_on_io(struct task_struct *p) { @@ -156,6 +163,18 @@ static inline void delayacct_freepages_end(void) __delayacct_freepages_end(); } +static inline void delayacct_thrashing_start(void) +{ + if (current->delays) + __delayacct_thrashing_start(); +} + +static inline void delayacct_thrashing_end(void) +{ + if (current->delays) + __delayacct_thrashing_end(); +} + #else static inline void delayacct_set_flag(int flag) {} @@ -182,6 +201,10 @@ static inline void delayacct_freepages_start(void) {} static inline void delayacct_freepages_end(void) {} +static inline void delayacct_thrashing_start(void) +{} +static inline void delayacct_thrashing_end(void) +{} #endif /* CONFIG_TASK_DELAY_ACCT */ diff --git a/include/uapi/linux/taskstats.h b/include/uapi/linux/taskstats.h index b7aa7bb2349f..5e8ca16a9079 100644 --- a/include/uapi/linux/taskstats.h +++ b/include/uapi/linux/taskstats.h @@ -34,7 +34,7 @@ */ -#define TASKSTATS_VERSION 8 +#define TASKSTATS_VERSION 9 #define TS_COMM_LEN 32 /* should be >= TASK_COMM_LEN * in linux/sched.h */ @@ -164,6 +164,10 @@ struct taskstats { /* Delay waiting for memory reclaim */ __u64 freepages_count; __u64 freepages_delay_total; + + /* Delay waiting for thrashing page */ + __u64 thrashing_count; + __u64 thrashing_delay_total; }; diff --git a/kernel/delayacct.c b/kernel/delayacct.c index e2764d767f18..02ba745c448d 100644 --- a/kernel/delayacct.c +++ b/kernel/delayacct.c @@ -134,9 +134,12 @@ int __delayacct_add_tsk(struct taskstats *d, struct task_struct *tsk) d->swapin_delay_total = (tmp < d->swapin_delay_total) ? 0 : tmp; tmp = d->freepages_delay_total + tsk->delays->freepages_delay; d->freepages_delay_total = (tmp < d->freepages_delay_total) ? 0 : tmp; + tmp = d->thrashing_delay_total + tsk->delays->thrashing_delay; + d->thrashing_delay_total = (tmp < d->thrashing_delay_total) ? 0 : tmp; d->blkio_count += tsk->delays->blkio_count; d->swapin_count += tsk->delays->swapin_count; d->freepages_count += tsk->delays->freepages_count; + d->thrashing_count += tsk->delays->thrashing_count; spin_unlock_irqrestore(&tsk->delays->lock, flags); return 0; @@ -168,3 +171,15 @@ void __delayacct_freepages_end(void) ¤t->delays->freepages_count); } +void __delayacct_thrashing_start(void) +{ + current->delays->thrashing_start = ktime_get_ns(); +} + +void __delayacct_thrashing_end(void) +{ + delayacct_end(¤t->delays->lock, + ¤t->delays->thrashing_start, + ¤t->delays->thrashing_delay, + ¤t->delays->thrashing_count); +} diff --git a/mm/filemap.c b/mm/filemap.c index bd36b7226cf4..e49961e13dd9 100644 --- a/mm/filemap.c +++ b/mm/filemap.c @@ -36,6 +36,7 @@ #include #include #include +#include #include "internal.h" #define CREATE_TRACE_POINTS @@ -1073,8 +1074,15 @@ static inline int wait_on_page_bit_common(wait_queue_head_t *q, { struct wait_page_queue wait_page; wait_queue_entry_t *wait = &wait_page.wait; + bool thrashing = false; int ret = 0; + if (bit_nr == PG_locked && !PageSwapBacked(page) && + !PageUptodate(page) && PageWorkingset(page)) { + delayacct_thrashing_start(); + thrashing = true; + } + init_wait(wait); wait->flags = lock ? WQ_FLAG_EXCLUSIVE : 0; wait->func = wake_page_function; @@ -1113,6 +1121,9 @@ static inline int wait_on_page_bit_common(wait_queue_head_t *q, finish_wait(q, wait); + if (thrashing) + delayacct_thrashing_end(); + /* * A signal could leave PageWaiters set. Clearing it here if * !waitqueue_active would be possible (by open-coding finish_wait), diff --git a/tools/accounting/getdelays.c b/tools/accounting/getdelays.c index 9f420d98b5fb..8cb504d30384 100644 --- a/tools/accounting/getdelays.c +++ b/tools/accounting/getdelays.c @@ -203,6 +203,8 @@ static void print_delayacct(struct taskstats *t) "SWAP %15s%15s%15s\n" " %15llu%15llu%15llums\n" "RECLAIM %12s%15s%15s\n" + " %15llu%15llu%15llums\n" + "THRASHING%12s%15s%15s\n" " %15llu%15llu%15llums\n", "count", "real total", "virtual total", "delay total", "delay average", @@ -222,7 +224,11 @@ static void print_delayacct(struct taskstats *t) "count", "delay total", "delay average", (unsigned long long)t->freepages_count, (unsigned long long)t->freepages_delay_total, - average_ms(t->freepages_delay_total, t->freepages_count)); + average_ms(t->freepages_delay_total, t->freepages_count), + "count", "delay total", "delay average", + (unsigned long long)t->thrashing_count, + (unsigned long long)t->thrashing_delay_total, + average_ms(t->thrashing_delay_total, t->thrashing_count)); } static void task_context_switch_counts(struct taskstats *t)