Received: by 2002:ac0:a5a6:0:0:0:0:0 with SMTP id m35-v6csp4550708imm; Tue, 11 Sep 2018 13:48:09 -0700 (PDT) X-Google-Smtp-Source: ANB0VdbIbwBrNStzIuoCV1U9p28sTqQpv/hIj/ceTWGC3rziwerMNBYB+bwi35utAkGqZFgNrwPd X-Received: by 2002:a17:902:64c1:: with SMTP id y1-v6mr28525206pli.45.1536698889131; Tue, 11 Sep 2018 13:48:09 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1536698889; cv=none; d=google.com; s=arc-20160816; b=bF3w7Ffm97cVJiGDZQ7LydxQmKTh2Rx55i0f0h7K6eXdr9vX4/mVY+OfJUwfo/nW6V hiu5fFLhwxMhyUjoh5Z3aJP6CneOvtzyUsqDU6zB5tF5A3NxbZawoAcvJjRyOW2vfmCb TIT9/+m/cTC1Dryo8kFpGaMHFznvpeZFZvT6QWmIGeKDkNsafhk2fF9tjTt6isNhnGXK i3VVDB3cgf8y5NNH8Jz2qTrmBab2872qBwzLaIEk6PElvxyzV2nugh1d5lbA7T7DYG9R kvIZS87qTVl6sWHAkpHDvxNseAo9MZTOp+pCAgkK9LbseIP5tR94whBdYv3xqHQhAMq2 +KQA== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:sender:subject:content-transfer-encoding :mime-version:organization:references:in-reply-to:date:cc:to:from :message-id; bh=dYFP2ACUKG7iWVK8eHUkSYHpqUS03AVmQdh8hPjUfys=; b=aiyZeDuw78/1prURrpMlbuDNuJR5M0vvnKkZ1nSzBtdx4mMTDg4YsqcV3YyyMpROWj /TgZ5IxsUbc5fbvZvlfCtIUJh1G8cnzW6hjHV5J7at7uTE+0TM80JRAnpqzjtoxDF133 q1+QPNJczZFgFJpTy7ndrmd3uW5XawBuPBbNuetyUQlHlQF2QjXq6OOW3K5xnlqvFlyG D8brhWn8Grx5d69C6tSEdmliCReZ1HB+L9LLLMUSg/gtD+8uLHwUkeb4tHjoIlQyV1V0 QC7qsksITBotwERWx8bONGNJBPpMUjM+p94EKs2JYDKCSFzmQBXmWIhXAHFyLWmKFi7o OOqw== ARC-Authentication-Results: i=1; mx.google.com; spf=pass (google.com: best guess record for domain of linux-kernel-owner@vger.kernel.org designates 209.132.180.67 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org Return-Path: Received: from vger.kernel.org (vger.kernel.org. [209.132.180.67]) by mx.google.com with ESMTP id i6-v6si21684511pfg.175.2018.09.11.13.47.53; Tue, 11 Sep 2018 13:48:09 -0700 (PDT) Received-SPF: pass (google.com: best guess record for domain of linux-kernel-owner@vger.kernel.org designates 209.132.180.67 as permitted sender) client-ip=209.132.180.67; Authentication-Results: mx.google.com; spf=pass (google.com: best guess record for domain of linux-kernel-owner@vger.kernel.org designates 209.132.180.67 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1727150AbeILBsh (ORCPT + 99 others); Tue, 11 Sep 2018 21:48:37 -0400 Received: from ou.quest-ce.net ([195.154.187.82]:43351 "EHLO ou.quest-ce.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726862AbeILBsh (ORCPT ); Tue, 11 Sep 2018 21:48:37 -0400 Received: from [2a01:e35:2e9f:6cb0:857c:11e6:3194:d53d] (helo=test.quest-ce.net) by ou.quest-ce.net with esmtpsa (TLS1.1:RSA_AES_256_CBC_SHA1:256) (Exim 4.80) (envelope-from ) id 1fzpZ8-000FMY-9v; Tue, 11 Sep 2018 22:47:21 +0200 Message-ID: From: Yann Droneaud To: Gerd Hoffmann , dri-devel@lists.freedesktop.org Cc: "open list:KERNEL SELFTEST FRAMEWORK" , Tomeu Vizoso , Jonathan Corbet , David Airlie , "open list:DOCUMENTATION" , open list , "moderated list:DMA BUFFER SHARING FRAMEWORK" , "open list:DMA BUFFER SHARING FRAMEWORK" , Shuah Khan , Laurent Pinchart , linux-api@vger.kernel.org Date: Tue, 11 Sep 2018 22:47:17 +0200 In-Reply-To: <20180827093444.23623-1-kraxel@redhat.com> References: <20180827093444.23623-1-kraxel@redhat.com> Organization: OPTEYA Content-Type: text/plain; charset="UTF-8" X-Mailer: Evolution 3.28.5 (3.28.5-1.fc28) Mime-Version: 1.0 Content-Transfer-Encoding: 8bit X-SA-Exim-Connect-IP: 2a01:e35:2e9f:6cb0:857c:11e6:3194:d53d X-SA-Exim-Mail-From: ydroneaud@opteya.com X-Spam-Checker-Version: SpamAssassin 3.3.2 (2011-06-06) on ou.quest-ce.net X-Spam-Level: X-Spam-Status: No, score=-2.9 required=5.0 tests=ALL_TRUSTED,BAYES_00, URIBL_BLOCKED autolearn=ham version=3.3.2 Subject: Re: [v7] Add udmabuf misc device X-SA-Exim-Version: 4.2.1 (built Mon, 26 Dec 2011 16:24:06 +0000) X-SA-Exim-Scanned: Yes (on ou.quest-ce.net) Sender: linux-kernel-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Hi, Le lundi 27 août 2018 à 11:34 +0200, Gerd Hoffmann a écrit : > A driver to let userspace turn memfd regions into dma-bufs. > > Use case: Allows qemu create dmabufs for the vga framebuffer or > virtio-gpu ressources. Then they can be passed around to display > those guest things on the host. To spice client for classic full > framebuffer display, and hopefully some day to wayland server for > seamless guest window display. > > qemu test branch: > https://git.kraxel.org/cgit/qemu/log/?h=sirius/udmabuf > > Cc: David Airlie > Cc: Tomeu Vizoso > Cc: Laurent Pinchart > Cc: Daniel Vetter > Signed-off-by: Gerd Hoffmann > Acked-by: Daniel Vetter > --- > Documentation/ioctl/ioctl-number.txt | 1 + > include/uapi/linux/udmabuf.h | 33 +++ > drivers/dma-buf/udmabuf.c | 287 > ++++++++++++++++++++++ > tools/testing/selftests/drivers/dma-buf/udmabuf.c | 96 ++++++++ > MAINTAINERS | 16 ++ > drivers/dma-buf/Kconfig | 8 + > drivers/dma-buf/Makefile | 1 + > tools/testing/selftests/drivers/dma-buf/Makefile | 5 + > 8 files changed, 447 insertions(+) > create mode 100644 include/uapi/linux/udmabuf.h > create mode 100644 drivers/dma-buf/udmabuf.c > create mode 100644 tools/testing/selftests/drivers/dma-buf/udmabuf.c > create mode 100644 tools/testing/selftests/drivers/dma-buf/Makefile > > diff --git a/include/uapi/linux/udmabuf.h > b/include/uapi/linux/udmabuf.h > new file mode 100644 > index 0000000000..46b6532ed8 > --- /dev/null > +++ b/include/uapi/linux/udmabuf.h > @@ -0,0 +1,33 @@ > +/* SPDX-License-Identifier: GPL-2.0 WITH Linux-syscall-note */ > +#ifndef _UAPI_LINUX_UDMABUF_H > +#define _UAPI_LINUX_UDMABUF_H > + > +#include > +#include > + > +#define UDMABUF_FLAGS_CLOEXEC 0x01 > + > +struct udmabuf_create { > + __u32 memfd; > + __u32 flags; > + __u64 offset; > + __u64 size; > +}; > + > +struct udmabuf_create_item { > + __u32 memfd; > + __u32 __pad; > + __u64 offset; > + __u64 size; > +}; > + > +struct udmabuf_create_list { > + __u32 flags; > + __u32 count; > + struct udmabuf_create_item list[]; > +}; > + > +#define UDMABUF_CREATE _IOW('u', 0x42, struct udmabuf_create) > +#define UDMABUF_CREATE_LIST _IOW('u', 0x43, struct > udmabuf_create_list) > + > +#endif /* _UAPI_LINUX_UDMABUF_H */ > diff --git a/drivers/dma-buf/udmabuf.c b/drivers/dma-buf/udmabuf.c > new file mode 100644 > index 0000000000..8e24204526 > --- /dev/null > +++ b/drivers/dma-buf/udmabuf.c > +static long udmabuf_create(struct udmabuf_create_list *head, > + struct udmabuf_create_item *list) > +{ > + DEFINE_DMA_BUF_EXPORT_INFO(exp_info); > + struct file *memfd = NULL; > + struct udmabuf *ubuf; > + struct dma_buf *buf; > + pgoff_t pgoff, pgcnt, pgidx, pgbuf; > + struct page *page; > + int seals, ret = -EINVAL; > + u32 i, flags; > + > + ubuf = kzalloc(sizeof(struct udmabuf), GFP_KERNEL); > + if (!ubuf) > + return -ENOMEM; > + > + for (i = 0; i < head->count; i++) { You need to check .__pad for unsupported value: if (list[i].__pad) { ret = -EINVAL; goto err_free_ubuf; } > + if (!IS_ALIGNED(list[i].offset, PAGE_SIZE)) > + goto err_free_ubuf; > + if (!IS_ALIGNED(list[i].size, PAGE_SIZE)) > + goto err_free_ubuf; > + ubuf->pagecount += list[i].size >> PAGE_SHIFT; > + } > + ubuf->pages = kmalloc_array(ubuf->pagecount, sizeof(struct page > *), > + GFP_KERNEL); > + if (!ubuf->pages) { > + ret = -ENOMEM; > + goto err_free_ubuf; > + } > + > + pgbuf = 0; > + for (i = 0; i < head->count; i++) { > + memfd = fget(list[i].memfd); > + if (!memfd) > + goto err_put_pages; > + if (!shmem_mapping(file_inode(memfd)->i_mapping)) > + goto err_put_pages; > + seals = memfd_fcntl(memfd, F_GET_SEALS, 0); > + if (seals == -EINVAL || > + (seals & SEALS_WANTED) != SEALS_WANTED || > + (seals & SEALS_DENIED) != 0) > + goto err_put_pages; > + pgoff = list[i].offset >> PAGE_SHIFT; > + pgcnt = list[i].size >> PAGE_SHIFT; > + for (pgidx = 0; pgidx < pgcnt; pgidx++) { > + page = shmem_read_mapping_page( > + file_inode(memfd)->i_mapping, pgoff + > pgidx); > + if (IS_ERR(page)) { > + ret = PTR_ERR(page); > + goto err_put_pages; > + } > + ubuf->pages[pgbuf++] = page; > + } > + fput(memfd); > + } > + memfd = NULL; > + > + exp_info.ops = &udmabuf_ops; > + exp_info.size = ubuf->pagecount << PAGE_SHIFT; > + exp_info.priv = ubuf; > + > + buf = dma_buf_export(&exp_info); > + if (IS_ERR(buf)) { > + ret = PTR_ERR(buf); > + goto err_put_pages; > + } > + > + flags = 0; You need to check .flags for unsupported value: if (head->flags & ~UDMABUF_FLAGS_CLOEXEC) return -EINVAL; (at the beginning of the function, of course). > + if (head->flags & UDMABUF_FLAGS_CLOEXEC) > + flags |= O_CLOEXEC; > + return dma_buf_fd(buf, flags); > + > +err_put_pages: > + while (pgbuf > 0) > + put_page(ubuf->pages[--pgbuf]); > +err_free_ubuf: > + fput(memfd); > + kfree(ubuf->pages); > + kfree(ubuf); > + return ret; > +} > + Regards -- Yann Droneaud OPTEYA