Blame README

Packit 345191
# **MEMKIND**
Packit 345191
Packit 345191
[![Build Status](https://travis-ci.org/memkind/memkind.svg)](https://travis-ci.org/memkind/memkind)
Packit 345191
[![MEMKIND version](https://img.shields.io/github/tag/memkind/memkind.svg)](https://github.com/memkind/memkind/releases/latest)
Packit 345191
[![Coverage Status](http://codecov.io/github/memkind/memkind/coverage.svg?branch=master)](http://codecov.io/gh/memkind/memkind?branch=master)
Packit 345191
[![Packaging status](https://repology.org/badge/tiny-repos/memkind.svg)](https://repology.org/project/memkind/versions)
Packit 345191
Packit 345191
The memkind library is a user extensible heap manager built on top of
Packit 345191
jemalloc which enables control of memory characteristics and a
Packit 345191
partitioning of the heap between kinds of memory.  The kinds of memory
Packit 345191
are defined by operating system memory policies that have been applied
Packit 345191
to virtual address ranges.  Memory characteristics supported by
Packit 345191
memkind without user extension include control of NUMA and page size
Packit 345191
features.  The jemalloc non-standard interface has been extended to
Packit 345191
enable specialized arenas to make requests for virtual memory from the
Packit 345191
operating system through the memkind partition interface.  Through the
Packit 345191
other memkind interfaces the user can control and extend memory
Packit 345191
partition features and allocate memory while selecting enabled
Packit 345191
features.  Memkind interface allows to create and control file-backed memory
Packit 345191
(PMEM kind) on specified device.
Packit 345191
Packit 345191
## Contents
Packit 345191
Packit 345191
1. [Interfaces](#interfaces)
Packit 345191
2. [Dependencies](#dependencies)
Packit 345191
3. [Building and Installing](#building-and-installing)
Packit 345191
	* [jemalloc](#jemalloc)
Packit 345191
4. [Run Requirements](#run-requirements)
Packit 345191
5. [Kind Requirements](#kind-requirements)
Packit 345191
6. [Kernel](#kernel)
Packit 345191
7. [NVDIMM volatile usage](#nvdimm-volatile-usage)
Packit 345191
	* [DAX device](#dax-device)
Packit 345191
	* [DAX filesystem](#dax-filesystem)
Packit 345191
8. [The Detection Mechanism of the Kind](#the-detection-mechanism-of-the-kind)
Packit 345191
9. [Setting Logging Mechanism](#setting-logging-mechanism)
Packit 345191
10. [Setting Heap Manager](#setting-heap-manager)
Packit 345191
11. [Testing](#testing)
Packit 345191
12. [Simulating High Bandwidth Memory](#simulating-high-bandwidth-memory)
Packit 345191
13. [Notes](#notes)
Packit 345191
14. [Status](#status)
Packit 345191
15. [Disclaimer](#disclaimer)
Packit 345191
Packit 345191
## Interfaces
Packit 345191
The memkind library delivers four interfaces:
Packit 345191
 * hbwmalloc.h - recommended for high-bandwidth memory use cases (stable)
Packit 345191
 * memkind.h - generic interface for more complex use cases (stable)
Packit 345191
 * pmem_allocator.h - the C++ allocator that satisfies the C++ Allocator
Packit 345191
   [requirements](https://en.cppreference.com/w/cpp/named_req/Allocator)
Packit 345191
   used for PMEM memory use cases (stable)
Packit 345191
 * memkind_allocator.h - the C++ allocator that satisfies the C++ Allocator
Packit 345191
   [requirements](https://en.cppreference.com/w/cpp/named_req/Allocator)
Packit 345191
   used for static kinds (stable)
Packit 345191
Packit 345191
For more detailed information about those interfaces see
Packit 345191
corresponding manpages (located in man/ subdir):
Packit 345191
Packit 345191
    man memkind
Packit 345191
Packit 345191
    man hbwmalloc
Packit 345191
Packit 345191
    man pmemallocator
Packit 345191
Packit 345191
    man memkindallocator
Packit 345191
Packit 345191
## Dependencies
Packit 345191
Packit 345191
You will need to install required packages on the build system:
Packit 345191
Packit 345191
* **autoconf**
Packit 345191
* **automake**
Packit 345191
* **gcc-c++**
Packit 345191
* **libnuma-devel**
Packit 345191
* **libtool**
Packit 345191
* **numactl-devel**
Packit 345191
* **unzip**
Packit 345191
Packit 345191
For using automatic recognition of PMEM NUMA in MEMKIND_DAX_KMEM:
Packit 345191
Packit 345191
* **libdaxctl-devel** (v66 or later)
Packit 345191
Packit 345191
## Building and Installing
Packit 345191
Packit 345191
The memkind library has a dependency on a related fork of jemalloc.
Packit 345191
The configure scripts and gtest source code are distributed with the
Packit 345191
source tarball included in the source RPM, and this tarball is created
Packit 345191
with the memkind "make dist" target. In contrast to the distributed source
Packit 345191
tarball, the git repository does not include any generated files.
Packit 345191
For this reason some additional steps are required when building
Packit 345191
from a checkout of the git repo. Those steps include running
Packit 345191
the bash script called "autogen.sh" prior to configure.  This script
Packit 345191
will populate a VERSION file based on "git describe", and use
Packit 345191
autoreconf to generate a configure script.
Packit 345191
Packit 345191
Building and installing memkind in standard system location can be as simple as
Packit 345191
typing the following while in the root directory of the source tree:
Packit 345191
Packit 345191
    ./autogen.sh
Packit 345191
    ./configure
Packit 345191
    make
Packit 345191
    make install
Packit 345191
Packit 345191
To install this library into **other locations**, you can use the prefix variable, e.g.:
Packit 345191
Packit 345191
    ./autogen.sh
Packit 345191
    ./configure --prefix=/usr
Packit 345191
    make
Packit 345191
    make install
Packit 345191
Packit 345191
This will install files to /usr/lib, /usr/include, /usr/share/doc/, usr/share/man.
Packit 345191
Packit 345191
See the output of:
Packit 345191
Packit 345191
    ./configure --help
Packit 345191
Packit 345191
for more information about either the memkind or the jemalloc configuration options.
Packit 345191
Packit 345191
## jemalloc
Packit 345191
The jemalloc source was forked from jemalloc version 5.2.1.  This source tree
Packit 345191
is located within the jemalloc subdirectory of the memkind source.  The jemalloc
Packit 345191
source code has been kept close to the original form, and in particular
Packit 345191
the build system has been lightly modified.
Packit 345191
Packit 345191
## Run Requirements
Packit 345191
Packit 345191
You will need to install required packages for applications,
Packit 345191
which are using the memkind library for dynamic linking at run time:
Packit 345191
Packit 345191
* **libnuma**
Packit 345191
* **numactl**
Packit 345191
* **pthread**
Packit 345191
Packit 345191
## Kind Requirements
Packit 345191
Packit 345191
| Memory kind                   | NUMA  |  HBW Memory | Hugepages | Device DAX | Filesystem supporting hole punching |
Packit 345191
| ----------------------------- |:-----:|:-----------:|:---------:|:----------:|:-----------------------------------:|
Packit 345191
| MEMKIND_DEFAULT               |       |             |           |            |                                     |
Packit 345191
| MEMKIND_HUGETLB               | X     | X           | X         |            |                                     |
Packit 345191
| MEMKIND_HBW                   | X     | X           |           |            |                                     |
Packit 345191
| MEMKIND_HBW_ALL               | X     | X           |           |            |                                     |
Packit 345191
| MEMKIND_HBW_HUGETLB           | X     | X           | X         |            |                                     |
Packit 345191
| MEMKIND_HBW_ALL_HUGETLB       | X     | X           | X         |            |                                     |
Packit 345191
| MEMKIND_HBW_PREFERRED         | X     | X           |           |            |                                     |
Packit 345191
| MEMKIND_HBW_PREFERRED_HUGETLB | X     | X           | X         |            |                                     |
Packit 345191
| MEMKIND_HBW_INTERLEAVE        | X     | X           |           |            |                                     |
Packit 345191
| MEMKIND_REGULAR               | X     |             |           |            |                                     |
Packit 345191
| MEMKIND_DAX_KMEM              | X     |             |           | X          |                                     |
Packit 345191
| MEMKIND_DAX_KMEM_ALL          | X     |             |           | X          |                                     |
Packit 345191
| MEMKIND_DAX_KMEM_PREFERRED    | X     |             |           | X          |                                     |
Packit 345191
| PMEM kind                     |       |             |           |            | X                                   |
Packit 345191
Packit 345191
## Kernel
Packit 345191
To correctly control of NUMA, huge pages and file-backed memory following
Packit 345191
requirements regarding Linux kernel must be satisfied:
Packit 345191
Packit 345191
* **NUMA**
Packit 345191
Packit 345191
Requires kernel
Packit 345191
[patch](https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?id=3964acd0dbec123aa0a621973a2a0580034b4788)
Packit 345191
introduced in Linux v3.11 that impacts
Packit 345191
functionality of the NUMA system calls.  Red Hat has back-ported this patch to the
Packit 345191
v3.10 kernel in the RHEL 7.0 GA release, so RHEL 7.0 onward supports
Packit 345191
memkind even though this kernel version predates v3.11.
Packit 345191
Packit 345191
* **Hugepages**
Packit 345191
Packit 345191
Functionality related to hugepages allocation require patches
Packit 345191
[patch1](https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?id=e0ec90ee7e6f6cbaa6d59ffb48d2a7af5e80e61d) and
Packit 345191
[patch2](https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?id=099730d67417dfee273e9b10ac2560ca7fac7eb9)
Packit 345191
Without them physical memory may end up being located on incorrect NUMA node.
Packit 345191
Packit 345191
* **2MB Pages**
Packit 345191
Packit 345191
To use the interfaces for obtaining 2MB pages please be sure to follow the instructions
Packit 345191
[here](https://www.kernel.org/doc/Documentation/vm/hugetlbpage.txt) and pay particular
Packit 345191
attention to the use of the procfs files:
Packit 345191
Packit 345191
    /proc/sys/vm/nr_hugepages
Packit 345191
    /proc/sys/vm/nr_overcommit_hugepages
Packit 345191
Packit 345191
for enabling the kernel's huge page pool.
Packit 345191
Packit 345191
* **Filesystem supporting hole punching**
Packit 345191
Packit 345191
To use the PMEM kind, please be sure that filesystem which is used for PMEM creation supports
Packit 345191
[FALLOC_FL_PUNCH_HOLE](http://man7.org/linux/man-pages/man2/fallocate.2.html) flag.
Packit 345191
Packit 345191
* **Device DAX**
Packit 345191
Packit 345191
To use MEMKIND_DAX_KMEM_* kinds you need at least Linux Kernel 5.1 (with enabled DEV_DAX_KMEM Kernel option) and created DAX device.
Packit 345191
If you have loaded dax_pmem_compat module instead of dax_pmem, please read
Packit 345191
[this](https://pmem.io/ndctl/daxctl-migrate-device-model.html) article and migrate device model
Packit 345191
to use alternative device dax drivers, e.g. kmem.
Packit 345191
Packit 345191
If you want to migrate device model type:
Packit 345191
Packit 345191
    daxctl migrate-device-model
Packit 345191
Packit 345191
To create a new DAX device you can type:
Packit 345191
Packit 345191
    ndctl create-namespace --mode=devdax --map=mem
Packit 345191
Packit 345191
To display a list of created devices:
Packit 345191
Packit 345191
    ndctl list
Packit 345191
Packit 345191
If you have already created device in another mode, you can reconfigure the device using:
Packit 345191
Packit 345191
    ndctl create-namespace --mode=devdax --map=mem --force -e namespaceX.Y
Packit 345191
Packit 345191
Where namespaceX.Y means namespace you want to reconfigure.
Packit 345191
Packit 345191
For more details about creating new namespace read [this](https://pmem.io/ndctl/ndctl-create-namespace.html).
Packit 345191
Packit 345191
Conversion from device dax to NUMA node can be performed using following commands:
Packit 345191
Packit 345191
    daxctl reconfigure-device daxX.Y --mode=system-ram
Packit 345191
Packit 345191
Where daxX.Y is DAX device you want to reconfigure.
Packit 345191
Packit 345191
This will migrate device from device_dax to kmem driver. After this step daxctl should be able to
Packit 345191
see devices in system-ram mode:
Packit 345191
Packit 345191
    daxctl list
Packit 345191
Packit 345191
Example output after reconfigure dax2.0 as system-ram:
Packit 345191
Packit 345191
    [
Packit 345191
      {
Packit 345191
        "chardev":"dax1.0",
Packit 345191
        "size":263182090240,
Packit 345191
        "target_node":3,
Packit 345191
        "mode":"devdax"
Packit 345191
      },
Packit 345191
      {
Packit 345191
        "chardev":"dax2.0",
Packit 345191
        "size":263182090240,
Packit 345191
        "target_node":4,
Packit 345191
        "mode":"system-ram"
Packit 345191
      }
Packit 345191
    ]
Packit 345191
Packit 345191
Also you should be able to check new NUMA node configuration by:
Packit 345191
Packit 345191
    numactl -H
Packit 345191
Packit 345191
Example output, where NUMA node 4 is NUMA node created from persistent memory:
Packit 345191
Packit 345191
    available: 3 nodes (0-1,4)
Packit 345191
    node 0 cpus: 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83
Packit 345191
    node 0 size: 192112 MB
Packit 345191
    node 0 free: 185575 MB
Packit 345191
    node 1 cpus: 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111
Packit 345191
    node 1 size: 193522 MB
Packit 345191
    node 1 free: 193107 MB
Packit 345191
    node 4 cpus:
Packit 345191
    node 4 size: 250880 MB
Packit 345191
    node 4 free: 250879 MB
Packit 345191
    node distances:
Packit 345191
    node   0   1   4
Packit 345191
      0:  10  21  17
Packit 345191
      1:  21  10  28
Packit 345191
      4:  17  28  10
Packit 345191
Packit 345191
## NVDIMM volatile usage
Packit 345191
Packit 345191
Memkind supports using persistent memory as an extension of DRAM.
Packit 345191
This volatile memory solution is provided by the library with two separate ways described below.
Packit 345191
Packit 345191
## DAX device
Packit 345191
Packit 345191
NVDIMM memory as DAX device is supported by MEMKIND_DAX_KMEM_* kinds. With this solution
Packit 345191
persistent memory will be seen in OS as separate NUMA nodes.
Packit 345191
Packit 345191
Memkind allows two ways to use this kind:
Packit 345191
Packit 345191
- first implicitly, by allowing memkind library for automatic recognition of NUMA nodes
Packit 345191
created from persistent memory using [libdaxctl-devel](#dependencies)
Packit 345191
- secondary explicitly, by using MEMKIND_DAX_KMEM_NODES environment variable set to
Packit 345191
comma separated list of NUMA nodes which will be treated as NUMA nodes created from persistent memory,
Packit 345191
this solution overrides the first one
Packit 345191
Packit 345191
## DAX filesystem
Packit 345191
PMEM kind supports the traditional malloc/free interfaces on a memory mapped file.
Packit 345191
This allows the use of [persistent memory](https://pmem.io/)
Packit 345191
as volatile memory, for cases where the region of persistent memory
Packit 345191
is useful to an application, but when the application doesn't need it to be persistent.
Packit 345191
PMEM kind is most useful when used with Direct Access storage
Packit 345191
[DAX](https://www.kernel.org/doc/Documentation/filesystems/dax.txt), which is
Packit 345191
memory-addressable persistent storage that supports load/store access without being paged via the system page cache.
Packit 345191
Packit 345191
Application using memkind library supports managing a data placement:
Packit 345191
Packit 345191
| Data placement | Memory kind               |
Packit 345191
|----------------|---------------------------|
Packit 345191
| PMEM (fsdax)   | PMEM kind                 |
Packit 345191
| PMEM (devdax)  | MEMKIND_DAX_KMEM kind     |
Packit 345191
| DRAM           | e.g. MEMKIND_DEFAULT kind |
Packit 345191
Packit 345191
Currently, the PMEM kind is supported only by the jemalloc heap manager.
Packit 345191
Packit 345191
## The Detection Mechanism of the Kind
Packit 345191
One of the notable features of the memkind is to detect the correct kind of previously allocated memory.
Packit 345191
Packit 345191
| Operations                                  | Memkind API function                   |
Packit 345191
|---------------------------------------------|----------------------------------------|
Packit 345191
| Freeing memory                              | memkind_free(kind, ptr)                |
Packit 345191
| Reallocating memory                         | memkind_realloc(kind, ptr, size)       |
Packit 345191
| Obtaining the size of allocated memory      | memkind_malloc_usable_size(kind, ptr)  |
Packit 345191
| Reallocating memory to reduce fragmentation | memkind_defrag_reallocate(kind, ptr)   |
Packit 345191
Packit 345191
Operations above could be unified for all used memory kinds
Packit 345191
by passing a NULL value as a kind to the functions mentioned above.
Packit 345191
Packit 345191
For more details, please see the following
Packit 345191
[example](https://github.com/memkind/memkind/blob/master/examples/pmem_free_with_unknown_kind.c).
Packit 345191
Packit 345191
**Important Notes:**
Packit 345191
The look up for correct kind could result in serious performance penalty,
Packit 345191
which can be avoided by specifying a correct kind explicitly.
Packit 345191
Packit 345191
## Setting Logging Mechanism
Packit 345191
In memkind library logging mechanism could be enabled by setting MEMKIND_DEBUG
Packit 345191
environment variable. Setting MEMKIND_DEBUG to "1" enables printing messages
Packit 345191
like errors and general information about environment to stderr.
Packit 345191
Packit 345191
## Setting Heap Manager
Packit 345191
In memkind library heap management can be adjusted with MEMKIND_HEAP_MANAGER
Packit 345191
environment variable, which allows for switching to one of the available
Packit 345191
heap managers.
Packit 345191
Values:
Packit 345191
- JEMALLOC - sets the jemalloc heap manager
Packit 345191
- TBB - sets Intel Threading Building Blocks heap manager. This option requires installed
Packit 345191
Intel Threading Building Blocks library.
Packit 345191
Packit 345191
If the MEMKIND_HEAP_MANAGER is not set then the jemalloc heap manager will be used by default.
Packit 345191
Packit 345191
## Testing
Packit 345191
All existing tests pass. For more information on how to execute tests
Packit 345191
see the [CONTRIBUTING](CONTRIBUTING) file.
Packit 345191
Packit 345191
When tests are run on a NUMA platform without high bandwidth memory
Packit 345191
the MEMKIND_HBW_NODES environment variable is used in conjunction with
Packit 345191
"numactl --membind" to force standard allocations to one NUMA node and
Packit 345191
high bandwidth allocations through a different NUMA node.  See next
Packit 345191
section for more details.
Packit 345191
Packit 345191
Packit 345191
## Simulating High Bandwidth Memory
Packit 345191
A method for testing for the benefit of high bandwidth memory on a
Packit 345191
dual socket Intel(R) Xeon(TM) system is to use the QPI bus to simulate
Packit 345191
slow memory.  This is not an accurate model of the bandwidth and
Packit 345191
latency characteristics of the Intel's 2nd generation Intel(R) Xeon Phi(TM)
Packit 345191
Product Family on package memory, but is a reasonable way to determine
Packit 345191
which data structures rely critically on bandwidth.
Packit 345191
Packit 345191
If the application a.out has been modified to use high bandwidth
Packit 345191
memory with the memkind library then this can be done with numactl as
Packit 345191
follows with the bash shell:
Packit 345191
Packit 345191
    export MEMKIND_HBW_NODES=0
Packit 345191
    numactl --membind=1 --cpunodebind=0 a.out
Packit 345191
Packit 345191
or with csh:
Packit 345191
Packit 345191
    setenv MEMKIND_HBW_NODES 0
Packit 345191
    numactl --membind=1 --cpunodebind=0 a.out
Packit 345191
Packit 345191
The MEMKIND_HBW_NODES environment variable set to zero will bind high
Packit 345191
bandwidth allocations to NUMA node 0.  The --membind=1 flag to numactl
Packit 345191
will bind standard allocations, static and stack variables to NUMA
Packit 345191
node 1.  The --cpunodebind=0 option to numactl will bind the process
Packit 345191
threads to CPUs associated with NUMA node 0.  With this configuration
Packit 345191
standard allocations will be fetched across the QPI bus, and high
Packit 345191
bandwidth allocations will be local to the process CPU.
Packit 345191
Packit 345191
## Notes
Packit 345191
* Using memkind with Transparent Huge Pages enabled may result in
Packit 345191
 undesirably high memory footprint. To avoid that disable THP using following
Packit 345191
 [instruction](https://www.kernel.org/doc/Documentation/vm/transhuge.txt)
Packit 345191
Packit 345191
## Status
Packit 345191
Different interfaces can represent different maturity level
Packit 345191
(as described in corresponding man pages).
Packit 345191
Feedback on design and implementation is greatly appreciated.
Packit 345191
Packit 345191
## Disclaimer
Packit 345191
SEE [COPYING](COPYING) FILE FOR LICENSE INFORMATION.
Packit 345191
Packit 345191
THIS SOFTWARE IS PROVIDED AS A DEVELOPMENT SNAPSHOT TO AID
Packit 345191
COLLABORATION AND WAS NOT ISSUED AS A RELEASED PRODUCT BY INTEL.