Skip to content

Commit 8676af1

Browse files
aslanbakirovtorvalds
authored andcommitted
mm: cma: NUMA node interface
I've noticed that there is no interface exposed by CMA which would let me to declare contigous memory on particular NUMA node. This patchset adds the ability to try to allocate contiguous memory on a specific node. It will fallback to other nodes if the specified one doesn't work. Implement a new method for declaring contigous memory on particular node and keep cma_declare_contiguous() as a wrapper. [[email protected]: build fix] Signed-off-by: Aslan Bakirov <[email protected]> Signed-off-by: Roman Gushchin <[email protected]> Signed-off-by: Andrew Morton <[email protected]> Acked-by: Michal Hocko <[email protected]> Cc: Andreas Schaufler <[email protected]> Cc: Mike Kravetz <[email protected]> Cc: Rik van Riel <[email protected]> Cc: Joonsoo Kim <[email protected]> Link: http://lkml.kernel.org/r/[email protected] Signed-off-by: Linus Torvalds <[email protected]>
1 parent 783fda8 commit 8676af1

File tree

4 files changed

+25
-10
lines changed

4 files changed

+25
-10
lines changed

include/linux/cma.h

Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44

55
#include <linux/init.h>
66
#include <linux/types.h>
7+
#include <linux/numa.h>
78

89
/*
910
* There is always at least global CMA area and a few optional
@@ -24,10 +25,19 @@ extern phys_addr_t cma_get_base(const struct cma *cma);
2425
extern unsigned long cma_get_size(const struct cma *cma);
2526
extern const char *cma_get_name(const struct cma *cma);
2627

27-
extern int __init cma_declare_contiguous(phys_addr_t base,
28+
extern int __init cma_declare_contiguous_nid(phys_addr_t base,
2829
phys_addr_t size, phys_addr_t limit,
2930
phys_addr_t alignment, unsigned int order_per_bit,
30-
bool fixed, const char *name, struct cma **res_cma);
31+
bool fixed, const char *name, struct cma **res_cma,
32+
int nid);
33+
static inline int __init cma_declare_contiguous(phys_addr_t base,
34+
phys_addr_t size, phys_addr_t limit,
35+
phys_addr_t alignment, unsigned int order_per_bit,
36+
bool fixed, const char *name, struct cma **res_cma)
37+
{
38+
return cma_declare_contiguous_nid(base, size, limit, alignment,
39+
order_per_bit, fixed, name, res_cma, NUMA_NO_NODE);
40+
}
3141
extern int cma_init_reserved_mem(phys_addr_t base, phys_addr_t size,
3242
unsigned int order_per_bit,
3343
const char *name,

include/linux/memblock.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -348,6 +348,9 @@ static inline int memblock_get_region_node(const struct memblock_region *r)
348348

349349
phys_addr_t memblock_phys_alloc_range(phys_addr_t size, phys_addr_t align,
350350
phys_addr_t start, phys_addr_t end);
351+
phys_addr_t memblock_alloc_range_nid(phys_addr_t size,
352+
phys_addr_t align, phys_addr_t start,
353+
phys_addr_t end, int nid, bool exact_nid);
351354
phys_addr_t memblock_phys_alloc_try_nid(phys_addr_t size, phys_addr_t align, int nid);
352355

353356
static inline phys_addr_t memblock_phys_alloc(phys_addr_t size,

mm/cma.c

Lines changed: 9 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -220,7 +220,7 @@ int __init cma_init_reserved_mem(phys_addr_t base, phys_addr_t size,
220220
}
221221

222222
/**
223-
* cma_declare_contiguous() - reserve custom contiguous area
223+
* cma_declare_contiguous_nid() - reserve custom contiguous area
224224
* @base: Base address of the reserved area optional, use 0 for any
225225
* @size: Size of the reserved area (in bytes),
226226
* @limit: End address of the reserved memory (optional, 0 for any).
@@ -229,6 +229,7 @@ int __init cma_init_reserved_mem(phys_addr_t base, phys_addr_t size,
229229
* @fixed: hint about where to place the reserved area
230230
* @name: The name of the area. See function cma_init_reserved_mem()
231231
* @res_cma: Pointer to store the created cma region.
232+
* @nid: nid of the free area to find, %NUMA_NO_NODE for any node
232233
*
233234
* This function reserves memory from early allocator. It should be
234235
* called by arch specific code once the early allocator (memblock or bootmem)
@@ -238,10 +239,11 @@ int __init cma_init_reserved_mem(phys_addr_t base, phys_addr_t size,
238239
* If @fixed is true, reserve contiguous area at exactly @base. If false,
239240
* reserve in range from @base to @limit.
240241
*/
241-
int __init cma_declare_contiguous(phys_addr_t base,
242+
int __init cma_declare_contiguous_nid(phys_addr_t base,
242243
phys_addr_t size, phys_addr_t limit,
243244
phys_addr_t alignment, unsigned int order_per_bit,
244-
bool fixed, const char *name, struct cma **res_cma)
245+
bool fixed, const char *name, struct cma **res_cma,
246+
int nid)
245247
{
246248
phys_addr_t memblock_end = memblock_end_of_DRAM();
247249
phys_addr_t highmem_start;
@@ -336,14 +338,14 @@ int __init cma_declare_contiguous(phys_addr_t base,
336338
* memory in case of failure.
337339
*/
338340
if (base < highmem_start && limit > highmem_start) {
339-
addr = memblock_phys_alloc_range(size, alignment,
340-
highmem_start, limit);
341+
addr = memblock_alloc_range_nid(size, alignment,
342+
highmem_start, limit, nid, false);
341343
limit = highmem_start;
342344
}
343345

344346
if (!addr) {
345-
addr = memblock_phys_alloc_range(size, alignment, base,
346-
limit);
347+
addr = memblock_alloc_range_nid(size, alignment, base,
348+
limit, nid, false);
347349
if (!addr) {
348350
ret = -ENOMEM;
349351
goto err;

mm/memblock.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1349,7 +1349,7 @@ __next_mem_pfn_range_in_zone(u64 *idx, struct zone *zone,
13491349
* Return:
13501350
* Physical address of allocated memory block on success, %0 on failure.
13511351
*/
1352-
static phys_addr_t __init memblock_alloc_range_nid(phys_addr_t size,
1352+
phys_addr_t __init memblock_alloc_range_nid(phys_addr_t size,
13531353
phys_addr_t align, phys_addr_t start,
13541354
phys_addr_t end, int nid,
13551355
bool exact_nid)

0 commit comments

Comments
 (0)