| 137 | } |
| 138 | |
| 139 | int copy_file_to_memfd(int fd, const char *name) { |
| 140 | if (!has_memfd_support()) { |
| 141 | return -ENOSYS; |
| 142 | } |
| 143 | struct stat64 fileInfo = {}; |
| 144 | if (fstat64(fd, &fileInfo) < 0) { |
| 145 | return -errno; |
| 146 | } |
| 147 | int64_t length = int64_t(fileInfo.st_size); |
| 148 | if (length <= 0) { |
| 149 | return -EINVAL; |
| 150 | } |
| 151 | if (length > 64 * 1024 * 1024) { |
| 152 | return -ENOMEM; |
| 153 | } |
| 154 | int64_t originOffset = lseek64(fd, 0, SEEK_CUR); |
| 155 | if (originOffset < 0) { |
| 156 | return -errno; |
| 157 | } |
| 158 | int memfd = (int) syscall(__NR_memfd_create, name ? name : "none", MFD_CLOEXEC | MFD_ALLOW_SEALING); |
| 159 | if (memfd == -1) { |
| 160 | return -errno; |
| 161 | } |
| 162 | if (ftruncate(memfd, length) == -1) { |
| 163 | int orig = errno; |
| 164 | close(memfd); |
| 165 | errno = orig; |
| 166 | return -orig; |
| 167 | } |
| 168 | if (lseek(fd, 0, SEEK_SET) < 0) { |
| 169 | int err = errno; |
| 170 | close(memfd); |
| 171 | return -err; |
| 172 | } |
| 173 | char buf[4096]; |
| 174 | ssize_t i; |
| 175 | while ((i = read(fd, buf, 4096)) > 0) { |
| 176 | write(memfd, buf, i); |
| 177 | } |
| 178 | if (i != 0) { |
| 179 | int err = errno; |
| 180 | lseek64(fd, originOffset, SEEK_SET); |
| 181 | close(memfd); |
| 182 | return -err; |
| 183 | } |
| 184 | lseek64(memfd, 0, SEEK_SET); |
| 185 | lseek64(fd, originOffset, SEEK_SET); |
| 186 | return memfd; |
| 187 | } |
nothing calls this directly
no test coverage detected