[PATCH v7 3/6] mm/gup: Introduce memfd_pin_folios() for pinning memfd folios (v7)
kernel test robot
lkp at intel.com
Tue Dec 12 13:21:03 UTC 2023
Hi Vivek,
kernel test robot noticed the following build errors:
[auto build test ERROR on akpm-mm/mm-everything]
url: https://github.com/intel-lab-lkp/linux/commits/Vivek-Kasireddy/udmabuf-Use-vmf_insert_pfn-and-VM_PFNMAP-for-handling-mmap/20231212-160312
base: https://git.kernel.org/pub/scm/linux/kernel/git/akpm/mm.git mm-everything
patch link: https://lore.kernel.org/r/20231212073803.3233055-4-vivek.kasireddy%40intel.com
patch subject: [PATCH v7 3/6] mm/gup: Introduce memfd_pin_folios() for pinning memfd folios (v7)
config: x86_64-allnoconfig (https://download.01.org/0day-ci/archive/20231212/202312122109.SxDFnBaq-lkp@intel.com/config)
compiler: gcc-12 (Debian 12.2.0-14) 12.2.0
reproduce (this is a W=1 build): (https://download.01.org/0day-ci/archive/20231212/202312122109.SxDFnBaq-lkp@intel.com/reproduce)
If you fix the issue in a separate patch/commit (i.e. not just a new version of
the same patch/commit), kindly add following tags
| Reported-by: kernel test robot <lkp at intel.com>
| Closes: https://lore.kernel.org/oe-kbuild-all/202312122109.SxDFnBaq-lkp@intel.com/
All errors (new ones prefixed by >>):
mm/gup.c: In function 'memfd_pin_folios':
>> mm/gup.c:3543:39: error: assignment to 'struct folio *' from incompatible pointer type 'struct page *' [-Werror=incompatible-pointer-types]
3543 | folio = memfd_alloc_folio(memfd, start_idx);
| ^
cc1: some warnings being treated as errors
vim +3543 mm/gup.c
3417
3418 /**
3419 * memfd_pin_folios() - pin folios associated with a memfd
3420 * @memfd: the memfd whose folios are to be pinned
3421 * @start: starting memfd offset
3422 * @nr_pages: number of pages from start to pin
3423 * @folios: array that receives pointers to the folios pinned.
3424 * Should be at-least nr_pages long.
3425 * @offsets: array that receives offsets of pages in their folios.
3426 * Should be at-least nr_pages long.
3427 *
3428 * Attempt to pin folios associated with a memfd; given that a memfd is
3429 * either backed by shmem or hugetlb, the folios can either be found in
3430 * the page cache or need to be allocated if necessary. Once the folios
3431 * are located, they are all pinned via FOLL_PIN and the @offsets array
3432 * is populated with offsets of the pages in their respective folios.
3433 * Therefore, for each page the caller requested, there will be a
3434 * corresponding entry in both @folios and @offsets. And, eventually,
3435 * these pinned folios need to be released either using unpin_user_pages()
3436 * or unpin_user_page().
3437 *
3438 * It must be noted that the folios may be pinned for an indefinite amount
3439 * of time. And, in most cases, the duration of time they may stay pinned
3440 * would be controlled by the userspace. This behavior is effectively the
3441 * same as using FOLL_LONGTERM with other GUP APIs.
3442 *
3443 * Returns number of folios pinned. This would be equal to the number of
3444 * pages requested. If no folios were pinned, it returns -errno.
3445 */
3446 long memfd_pin_folios(struct file *memfd, unsigned long start,
3447 unsigned long nr_pages, struct folio **folios,
3448 pgoff_t *offsets)
3449 {
3450 unsigned long end = start + (nr_pages << PAGE_SHIFT) - 1;
3451 unsigned int max_pgs, pgoff, pgshift = PAGE_SHIFT;
3452 pgoff_t start_idx, end_idx, next_idx;
3453 unsigned int flags, nr_folios, i, j;
3454 struct folio *folio = NULL;
3455 struct folio_batch fbatch;
3456 struct page **pages;
3457 struct hstate *h;
3458 long ret;
3459
3460 if (!nr_pages)
3461 return -EINVAL;
3462
3463 if (!memfd)
3464 return -EINVAL;
3465
3466 if (!shmem_file(memfd) && !is_file_hugepages(memfd))
3467 return -EINVAL;
3468
3469 pages = kmalloc_array(nr_pages, sizeof(*pages), GFP_KERNEL);
3470 if (!pages)
3471 return -ENOMEM;
3472
3473 if (is_file_hugepages(memfd)) {
3474 h = hstate_file(memfd);
3475 pgshift = huge_page_shift(h);
3476 }
3477
3478 flags = memalloc_pin_save();
3479 do {
3480 i = 0;
3481 start_idx = start >> pgshift;
3482 end_idx = end >> pgshift;
3483 if (is_file_hugepages(memfd)) {
3484 start_idx <<= huge_page_order(h);
3485 end_idx <<= huge_page_order(h);
3486 }
3487
3488 folio_batch_init(&fbatch);
3489 while (start_idx <= end_idx) {
3490 /*
3491 * In most cases, we should be able to find the folios
3492 * in the page cache. If we cannot find them for some
3493 * reason, we try to allocate them and add them to the
3494 * page cache.
3495 */
3496 nr_folios = filemap_get_folios_contig(memfd->f_mapping,
3497 &start_idx,
3498 end_idx,
3499 &fbatch);
3500 if (folio) {
3501 folio_put(folio);
3502 folio = NULL;
3503 }
3504
3505 next_idx = 0;
3506 for (j = 0; j < nr_folios; j++) {
3507 if (next_idx &&
3508 next_idx != folio_index(fbatch.folios[j]))
3509 continue;
3510
3511 folio = try_grab_folio(&fbatch.folios[j]->page,
3512 1, FOLL_PIN);
3513 if (!folio) {
3514 folio_batch_release(&fbatch);
3515 kfree(pages);
3516 goto err;
3517 }
3518
3519 max_pgs = folio_nr_pages(folio);
3520 if (i == 0) {
3521 pgoff = offset_in_folio(folio, start);
3522 pgoff >>= PAGE_SHIFT;
3523 }
3524
3525 do {
3526 folios[i] = folio;
3527 offsets[i] = pgoff << PAGE_SHIFT;
3528 pages[i] = folio_page(folio, 0);
3529 folio_add_pin(folio);
3530
3531 pgoff++;
3532 i++;
3533 } while (pgoff < max_pgs && i < nr_pages);
3534
3535 pgoff = 0;
3536 next_idx = folio_next_index(folio);
3537 gup_put_folio(folio, 1, FOLL_PIN);
3538 }
3539
3540 folio = NULL;
3541 folio_batch_release(&fbatch);
3542 if (!nr_folios) {
> 3543 folio = memfd_alloc_folio(memfd, start_idx);
--
0-DAY CI Kernel Test Service
https://github.com/intel/lkp-tests/wiki
More information about the dri-devel
mailing list