Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit ea4b5cb

Browse files
fix(mmap): support read-only maps properly (#10782)
Only do msync on munmap if PROT_WRITE is set. If we lack permissions to msync, don't try and throw an error.
1 parent 42da364 commit ea4b5cb

File tree

3 files changed

+43
-2
lines changed

3 files changed

+43
-2
lines changed

src/library_syscall.js

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -259,7 +259,7 @@ var SyscallsLibrary = {
259259
#if CAN_ADDRESS_2GB
260260
ptr >>>= 0;
261261
#endif
262-
SYSCALLS.mappings[ptr] = { malloc: ptr, len: len, allocated: allocated, fd: fd, flags: flags, offset: off };
262+
SYSCALLS.mappings[ptr] = { malloc: ptr, len: len, allocated: allocated, fd: fd, prot: prot, flags: flags, offset: off };
263263
return ptr;
264264
},
265265

@@ -281,7 +281,9 @@ var SyscallsLibrary = {
281281
if (len === info.len) {
282282
#if FILESYSTEM && SYSCALLS_REQUIRE_FILESYSTEM
283283
var stream = FS.getStream(info.fd);
284-
SYSCALLS.doMsync(addr, stream, len, info.flags, info.offset);
284+
if (info.prot & {{{ cDefine('PROT_WRITE') }}}) {
285+
SYSCALLS.doMsync(addr, stream, len, info.flags, info.offset);
286+
}
285287
FS.munmap(stream);
286288
#else
287289
#if ASSERTIONS

tests/fs/test_mmap.c

Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -89,6 +89,44 @@ int main() {
8989
fclose(fd);
9090
}
9191

92+
// Use mmap to read out.txt and modify the contents in memory,
93+
// but make sure it's not overwritten on munmap
94+
{
95+
const char* readonlytext = "readonly mmap\0";
96+
const char* text = "write mmap\0";
97+
const char* path = "/yolo/outreadonly.txt";
98+
size_t readonlytextsize = strlen(readonlytext);
99+
size_t textsize = strlen(text);
100+
101+
int fd = open(path, O_RDWR | O_CREAT, (mode_t)0600);
102+
// write contents to the file ( we don't want this to be overwritten on munmap )
103+
assert(write(fd, readonlytext, readonlytextsize) != -1);
104+
close(fd);
105+
106+
fd = open(path, O_RDWR);
107+
char *map = (char*)mmap(0, textsize, PROT_READ, MAP_SHARED, fd, 0);
108+
assert(map != MAP_FAILED);
109+
110+
for (size_t i = 0; i < textsize; i++) {
111+
map[i] = text[i];
112+
}
113+
114+
assert(munmap(map, textsize) != -1);
115+
close(fd);
116+
}
117+
118+
{
119+
FILE* fd = fopen("/yolo/outreadonly.txt", "r");
120+
if (fd == NULL) {
121+
printf("failed to open /yolo/outreadonly.txt\n");
122+
return 1;
123+
}
124+
char buffer[14];
125+
fread(buffer, 1, 15, fd);
126+
printf("/yolo/outreadonly.txt content=%s\n", buffer);
127+
fclose(fd);
128+
}
129+
92130
// MAP_PRIVATE
93131
{
94132
const char* text = "written mmap";

tests/fs/test_mmap.out

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
/yolo/in.txt content=mmap ftw!
22
/yolo/out.txt content=written mmap
3+
/yolo/outreadonly.txt content=readonly mmap
34
/yolo/private.txt content=
45
/yolo/sharedoffset.txt content=written shared mmap with offset 32768

0 commit comments

Comments
 (0)