From nobody Tue May 13 14:49:15 2025 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of redhat.com designates 209.132.183.28 as permitted sender) client-ip=209.132.183.28; envelope-from=libvir-list-bounces@redhat.com; helo=mx1.redhat.com; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of redhat.com designates 209.132.183.28 as permitted sender) smtp.mailfrom=libvir-list-bounces@redhat.com; dmarc=fail(p=none dis=none) header.from=intel.com Return-Path: Received: from mx1.redhat.com (mx1.redhat.com [209.132.183.28]) by mx.zohomail.com with SMTPS id 1539081163135179.5871097247034; Tue, 9 Oct 2018 03:32:43 -0700 (PDT) Received: from smtp.corp.redhat.com (int-mx02.intmail.prod.int.phx2.redhat.com [10.5.11.12]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 5346F88E58; Tue, 9 Oct 2018 10:32:41 +0000 (UTC) Received: from colo-mx.corp.redhat.com (colo-mx02.intmail.prod.int.phx2.redhat.com [10.5.11.21]) by smtp.corp.redhat.com (Postfix) with ESMTPS id 10CB66EE3B; Tue, 9 Oct 2018 10:32:41 +0000 (UTC) Received: from lists01.pubmisc.prod.ext.phx2.redhat.com (lists01.pubmisc.prod.ext.phx2.redhat.com [10.5.19.33]) by colo-mx.corp.redhat.com (Postfix) with ESMTP id AC7034CAA8; Tue, 9 Oct 2018 10:32:40 +0000 (UTC) Received: from smtp.corp.redhat.com (int-mx08.intmail.prod.int.phx2.redhat.com [10.5.11.23]) by lists01.pubmisc.prod.ext.phx2.redhat.com (8.13.8/8.13.8) with ESMTP id w99AWZcX008138 for ; Tue, 9 Oct 2018 06:32:35 -0400 Received: by smtp.corp.redhat.com (Postfix) id C1E4E5B2C4; Tue, 9 Oct 2018 10:32:35 +0000 (UTC) Received: from mx1.redhat.com (ext-mx04.extmail.prod.ext.phx2.redhat.com [10.5.110.28]) by smtp.corp.redhat.com (Postfix) with ESMTPS id B6E3F5B2DC for ; Tue, 9 Oct 2018 10:32:32 +0000 (UTC) Received: from mga06.intel.com (mga06.intel.com [134.134.136.31]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 971968831C for ; Tue, 9 Oct 2018 10:32:31 +0000 (UTC) Received: from orsmga002.jf.intel.com ([10.7.209.21]) by orsmga104.jf.intel.com with ESMTP/TLS/DHE-RSA-AES256-GCM-SHA384; 09 Oct 2018 03:32:25 -0700 Received: from david-unc.bj.intel.com ([10.238.145.63]) by orsmga002.jf.intel.com with ESMTP; 09 Oct 2018 03:32:17 -0700 X-Amp-Result: SKIPPED(no attachment in message) X-Amp-File-Uploaded: False X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.54,360,1534834800"; d="scan'208";a="98690439" From: Wang Huaqiang To: libvir-list@redhat.com Date: Tue, 9 Oct 2018 18:30:35 +0800 Message-Id: <1539081045-6769-10-git-send-email-huaqiang.wang@intel.com> In-Reply-To: <1539081045-6769-1-git-send-email-huaqiang.wang@intel.com> References: <1539081045-6769-1-git-send-email-huaqiang.wang@intel.com> X-Greylist: Sender passed SPF test, Sender IP whitelisted by DNSRBL, ACL 214 matched, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.5.110.28]); Tue, 09 Oct 2018 10:32:31 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.5.110.28]); Tue, 09 Oct 2018 10:32:31 +0000 (UTC) for IP:'134.134.136.31' DOMAIN:'mga06.intel.com' HELO:'mga06.intel.com' FROM:'huaqiang.wang@intel.com' RCPT:'' X-RedHat-Spam-Score: -2.301 (RCVD_IN_DNSWL_MED, SPF_PASS) 134.134.136.31 mga06.intel.com 134.134.136.31 mga06.intel.com X-Scanned-By: MIMEDefang 2.78 on 10.5.110.28 X-Scanned-By: MIMEDefang 2.84 on 10.5.11.23 X-loop: libvir-list@redhat.com Cc: shaohe.feng@intel.com, huaqiang.wang@intel.com, bing.niu@intel.com, jian-feng.ding@intel.com, rui.zang@intel.com Subject: [libvirt] [PATCHv5 09/19] util: Add more interfaces for resctrl monitor X-BeenThere: libvir-list@redhat.com X-Mailman-Version: 2.1.12 Precedence: junk List-Id: Development discussions about the libvirt library & tools List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Sender: libvir-list-bounces@redhat.com Errors-To: libvir-list-bounces@redhat.com X-Scanned-By: MIMEDefang 2.79 on 10.5.11.12 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.5.110.25]); Tue, 09 Oct 2018 10:32:42 +0000 (UTC) X-ZohoMail: RDMRC_1 RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" Add interfaces monitor group to support operations such as add PID, set ID, remove group ... etc. The interface for getting cache occupancy information from the monitor is also added. Signed-off-by: Wang Huaqiang --- src/libvirt_private.syms | 6 ++ src/util/virresctrl.c | 209 +++++++++++++++++++++++++++++++++++++++++++= +++- src/util/virresctrl.h | 23 ++++++ 3 files changed, 236 insertions(+), 2 deletions(-) diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms index a878083..c93d19f 100644 --- a/src/libvirt_private.syms +++ b/src/libvirt_private.syms @@ -2683,7 +2683,13 @@ virResctrlInfoNew; virResctrlMonitorAddPID; virResctrlMonitorCreate; virResctrlMonitorDeterminePath; +virResctrlMonitorGetCacheLevel; +virResctrlMonitorGetCacheOccupancy; +virResctrlMonitorGetID; virResctrlMonitorNew; +virResctrlMonitorRemove; +virResctrlMonitorSetCacheLevel; +virResctrlMonitorSetID; =20 =20 # util/virrotatingfile.h diff --git a/src/util/virresctrl.c b/src/util/virresctrl.c index b3d20cc..fca1f6f 100644 --- a/src/util/virresctrl.c +++ b/src/util/virresctrl.c @@ -225,11 +225,19 @@ virResctrlInfoMonFree(virResctrlInfoMonPtr mon) } =20 =20 + +/* + * virResctrlAlloc and virResctrlMonitor are representing a resource contr= ol + * group (in XML under cputune/cachetune and consequently a directory under + * /sys/fs/resctrl). virResctrlAlloc is the data structure for resource + * allocation, while the virResctrlMonitor represents the resource monitor= ing + * part. + */ + /* virResctrlAlloc */ =20 /* - * virResctrlAlloc represents one allocation (in XML under cputune/cachetu= ne and - * consequently a directory under /sys/fs/resctrl). Since it can have mul= tiple + * virResctrlAlloc represents one allocation. Since it can have multiple * parts of multiple caches allocated it is represented as bunch of nested * sparse arrays (by sparse I mean array of pointers so that each might be= NULL * in case there is no allocation for that particular cache allocation (le= vel, @@ -347,6 +355,8 @@ struct _virResctrlMonitor { /* libvirt-generated path in /sys/fs/resctrl for this particular * monitor */ char *path; + /* The cache 'level', special for cache monitor */ + unsigned int cache_level; }; =20 =20 @@ -2510,6 +2520,27 @@ virResctrlMonitorDeterminePath(virResctrlMonitorPtr = monitor, =20 =20 int +virResctrlMonitorSetID(virResctrlMonitorPtr monitor, + const char *id) +{ + if (!id) { + virReportError(VIR_ERR_INTERNAL_ERROR, "%s", + _("Resctrl monitor 'id' cannot be NULL")); + return -1; + } + + return VIR_STRDUP(monitor->id, id); +} + + +const char * +virResctrlMonitorGetID(virResctrlMonitorPtr monitor) +{ + return monitor->id; +} + + +int virResctrlMonitorCreate(virResctrlAllocPtr alloc, virResctrlMonitorPtr monitor, const char *machinename) @@ -2534,3 +2565,177 @@ virResctrlMonitorCreate(virResctrlAllocPtr alloc, virResctrlUnlock(lockfd); return ret; } + + +int +virResctrlMonitorRemove(virResctrlMonitorPtr monitor) +{ + int ret =3D 0; + + if (!monitor->path) + return 0; + + VIR_DEBUG("Removing resctrl monitor%s", monitor->path); + if (rmdir(monitor->path) !=3D 0 && errno !=3D ENOENT) { + virReportSystemError(errno, + _("Unable to remove %s (%d)"), + monitor->path, errno); + ret =3D -errno; + VIR_ERROR(_("Unable to remove %s (%d)"), monitor->path, errno); + } + + return ret; +} + + +int +virResctrlMonitorSetCacheLevel(virResctrlMonitorPtr monitor, + unsigned int level) +{ + /* Only supports cache level 3 CMT */ + if (level !=3D 3) { + virReportError(VIR_ERR_INTERNAL_ERROR, "%s", + _("Invalid resctrl monitor cache level")); + return -1; + } + + monitor->cache_level =3D level; + + return 0; +} + +unsigned int +virResctrlMonitorGetCacheLevel(virResctrlMonitorPtr monitor) +{ + return monitor->cache_level; +} + + +/* + * virResctrlMonitorGetStatistic + * + * @monitor: The monitor that the statistic data will be retrieved from. + * @resource: The name for resource name. 'llc_occpancy' for cache resourc= e. + * "mbm_totol_bytes" and "mbm_local_bytes" for memory bandwidth resource. + * @len: The array length for @ids, and @vals + * @ids: The id array for resource statistic information, ids[0] + * stores the first node id value, ids[1] stores the second node id value, + * ... and so on. + * @vals: The resource resource utilization information array. vals[0] + * stores the cache or memory bandwidth utilization value for first node, + * vals[1] stores the second value ... and so on. + * + * Get cache or memory bandwidth utilization information from monitor that + * specified by @id. + * + * Returns 0 for success, -1 for error. + */ +static int +virResctrlMonitorGetStatistic(virResctrlMonitorPtr monitor, + const char *resource, + size_t *len, + unsigned int **ids, + unsigned int **vals) +{ + int rv =3D -1; + int ret =3D -1; + size_t nids =3D 0; + size_t nvals =3D 0; + DIR *dirp =3D NULL; + char *datapath =3D NULL; + struct dirent *ent =3D NULL; + + if (!monitor) { + virReportError(VIR_ERR_INTERNAL_ERROR, "%s", + _("Invalid resctrl monitor")); + return -1; + } + + if (virAsprintf(&datapath, "%s/mon_data", monitor->path) < 0) + return -1; + + if (virDirOpen(&dirp, datapath) < 0) + goto cleanup; + + *len =3D 0; + while (virDirRead(dirp, &ent, datapath) > 0) { + char *str_id =3D NULL; + unsigned int id =3D 0; + unsigned int val =3D 0; + size_t i =3D 0; + size_t cur_id_pos =3D 0; + unsigned int tmp_id =3D 0; + unsigned int tmp_val =3D 0; + + /* Looking for directory that contains resource utilization + * information file. The directory name is arranged in format + * "mon__". For example, "mon_L3_00" and + * "mon_l3_01" are two target directories for a two nodes system + * with resource utilization data file for each node respectively. + */ + if (ent->d_type !=3D DT_DIR) + continue; + + if (STRNEQLEN(ent->d_name, "mon_L", 5)) + continue; + + str_id =3D strchr(ent->d_name, '_'); + if (!str_id) + continue; + + str_id =3D strchr(++str_id, '_'); + if (!str_id) + continue; + + if (virStrToLong_uip(++str_id, NULL, 0, &id) < 0) + goto cleanup; + + rv =3D virFileReadValueUint(&val, "%s/%s/%s", datapath, + ent->d_name, resource); + if (rv =3D=3D -2) { + virReportError(VIR_ERR_INTERNAL_ERROR, + _("File '%s/%s/%s' does not exist."), + datapath, ent->d_name, resource); + } + if (rv < 0) + goto cleanup; + + if (VIR_APPEND_ELEMENT(*ids, nids, id) < 0) + goto cleanup; + + if (VIR_APPEND_ELEMENT(*vals, nvals, val) < 0) + goto cleanup; + + /* Sort @ids and @vals arrays in the ascending order of id */ + cur_id_pos =3D nids - 1; + for (i =3D 0; i < cur_id_pos; i++) { + if ((*ids)[cur_id_pos] < (*ids)[i]) { + tmp_id =3D (*ids)[cur_id_pos]; + tmp_val =3D (*vals)[cur_id_pos]; + (*ids)[cur_id_pos] =3D (*ids)[i]; + (*vals)[cur_id_pos] =3D (*vals)[i]; + (*ids)[i] =3D tmp_id; + (*vals)[i] =3D tmp_val; + } + } + } + + *len =3D nids; + ret =3D 0; + cleanup: + VIR_FREE(datapath); + VIR_DIR_CLOSE(dirp); + return ret; +} + + +/* Get cache occupancy data from @monitor */ +int +virResctrlMonitorGetCacheOccupancy(virResctrlMonitorPtr monitor, + size_t *nbank, + unsigned int **bankids, + unsigned int **bankcaches) +{ + return virResctrlMonitorGetStatistic(monitor, "llc_occupancy", + nbank, bankids, bankcaches); +} diff --git a/src/util/virresctrl.h b/src/util/virresctrl.h index 1efe394..6137fee 100644 --- a/src/util/virresctrl.h +++ b/src/util/virresctrl.h @@ -202,7 +202,30 @@ virResctrlMonitorDeterminePath(virResctrlMonitorPtr mo= nitor, const char *machinename); =20 int +virResctrlMonitorSetID(virResctrlMonitorPtr monitor, + const char *id); + +const char * +virResctrlMonitorGetID(virResctrlMonitorPtr monitor); + +int virResctrlMonitorCreate(virResctrlAllocPtr alloc, virResctrlMonitorPtr monitor, const char *machinename); + +int +virResctrlMonitorRemove(virResctrlMonitorPtr monitor); + +int +virResctrlMonitorSetCacheLevel(virResctrlMonitorPtr monitor, + unsigned int level); + +unsigned int +virResctrlMonitorGetCacheLevel(virResctrlMonitorPtr monitor); + +int +virResctrlMonitorGetCacheOccupancy(virResctrlMonitorPtr monitor, + size_t *nbank, + unsigned int **bankids, + unsigned int **bankcaches); #endif /* __VIR_RESCTRL_H__ */ --=20 2.7.4 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list