diff options
295 files changed, 2809 insertions, 1261 deletions
diff --git a/Documentation/networking/snmp_counter.rst b/Documentation/networking/snmp_counter.rst index f8eb77ddbd44..b0dfdaaca512 100644 --- a/Documentation/networking/snmp_counter.rst +++ b/Documentation/networking/snmp_counter.rst | |||
@@ -571,7 +571,97 @@ duplicate packet is received. | |||
571 | 571 | ||
572 | * TcpExtTCPDSACKOfoRecv | 572 | * TcpExtTCPDSACKOfoRecv |
573 | The TCP stack receives a DSACK, which indicate an out of order | 573 | The TCP stack receives a DSACK, which indicate an out of order |
574 | duplciate packet is received. | 574 | duplicate packet is received. |
575 | |||
576 | TCP out of order | ||
577 | =============== | ||
578 | * TcpExtTCPOFOQueue | ||
579 | The TCP layer receives an out of order packet and has enough memory | ||
580 | to queue it. | ||
581 | |||
582 | * TcpExtTCPOFODrop | ||
583 | The TCP layer receives an out of order packet but doesn't have enough | ||
584 | memory, so drops it. Such packets won't be counted into | ||
585 | TcpExtTCPOFOQueue. | ||
586 | |||
587 | * TcpExtTCPOFOMerge | ||
588 | The received out of order packet has an overlay with the previous | ||
589 | packet. the overlay part will be dropped. All of TcpExtTCPOFOMerge | ||
590 | packets will also be counted into TcpExtTCPOFOQueue. | ||
591 | |||
592 | TCP PAWS | ||
593 | ======= | ||
594 | PAWS (Protection Against Wrapped Sequence numbers) is an algorithm | ||
595 | which is used to drop old packets. It depends on the TCP | ||
596 | timestamps. For detail information, please refer the `timestamp wiki`_ | ||
597 | and the `RFC of PAWS`_. | ||
598 | |||
599 | .. _RFC of PAWS: https://tools.ietf.org/html/rfc1323#page-17 | ||
600 | .. _timestamp wiki: https://en.wikipedia.org/wiki/Transmission_Control_Protocol#TCP_timestamps | ||
601 | |||
602 | * TcpExtPAWSActive | ||
603 | Packets are dropped by PAWS in Syn-Sent status. | ||
604 | |||
605 | * TcpExtPAWSEstab | ||
606 | Packets are dropped by PAWS in any status other than Syn-Sent. | ||
607 | |||
608 | TCP ACK skip | ||
609 | =========== | ||
610 | In some scenarios, kernel would avoid sending duplicate ACKs too | ||
611 | frequently. Please find more details in the tcp_invalid_ratelimit | ||
612 | section of the `sysctl document`_. When kernel decides to skip an ACK | ||
613 | due to tcp_invalid_ratelimit, kernel would update one of below | ||
614 | counters to indicate the ACK is skipped in which scenario. The ACK | ||
615 | would only be skipped if the received packet is either a SYN packet or | ||
616 | it has no data. | ||
617 | |||
618 | .. _sysctl document: https://www.kernel.org/doc/Documentation/networking/ip-sysctl.txt | ||
619 | |||
620 | * TcpExtTCPACKSkippedSynRecv | ||
621 | The ACK is skipped in Syn-Recv status. The Syn-Recv status means the | ||
622 | TCP stack receives a SYN and replies SYN+ACK. Now the TCP stack is | ||
623 | waiting for an ACK. Generally, the TCP stack doesn't need to send ACK | ||
624 | in the Syn-Recv status. But in several scenarios, the TCP stack need | ||
625 | to send an ACK. E.g., the TCP stack receives the same SYN packet | ||
626 | repeately, the received packet does not pass the PAWS check, or the | ||
627 | received packet sequence number is out of window. In these scenarios, | ||
628 | the TCP stack needs to send ACK. If the ACk sending frequency is higher than | ||
629 | tcp_invalid_ratelimit allows, the TCP stack will skip sending ACK and | ||
630 | increase TcpExtTCPACKSkippedSynRecv. | ||
631 | |||
632 | |||
633 | * TcpExtTCPACKSkippedPAWS | ||
634 | The ACK is skipped due to PAWS (Protect Against Wrapped Sequence | ||
635 | numbers) check fails. If the PAWS check fails in Syn-Recv, Fin-Wait-2 | ||
636 | or Time-Wait statuses, the skipped ACK would be counted to | ||
637 | TcpExtTCPACKSkippedSynRecv, TcpExtTCPACKSkippedFinWait2 or | ||
638 | TcpExtTCPACKSkippedTimeWait. In all other statuses, the skipped ACK | ||
639 | would be counted to TcpExtTCPACKSkippedPAWS. | ||
640 | |||
641 | * TcpExtTCPACKSkippedSeq | ||
642 | The sequence number is out of window and the timestamp passes the PAWS | ||
643 | check and the TCP status is not Syn-Recv, Fin-Wait-2, and Time-Wait. | ||
644 | |||
645 | * TcpExtTCPACKSkippedFinWait2 | ||
646 | The ACK is skipped in Fin-Wait-2 status, the reason would be either | ||
647 | PAWS check fails or the received sequence number is out of window. | ||
648 | |||
649 | * TcpExtTCPACKSkippedTimeWait | ||
650 | Tha ACK is skipped in Time-Wait status, the reason would be either | ||
651 | PAWS check failed or the received sequence number is out of window. | ||
652 | |||
653 | * TcpExtTCPACKSkippedChallenge | ||
654 | The ACK is skipped if the ACK is a challenge ACK. The RFC 5961 defines | ||
655 | 3 kind of challenge ACK, please refer `RFC 5961 section 3.2`_, | ||
656 | `RFC 5961 section 4.2`_ and `RFC 5961 section 5.2`_. Besides these | ||
657 | three scenarios, In some TCP status, the linux TCP stack would also | ||
658 | send challenge ACKs if the ACK number is before the first | ||
659 | unacknowledged number (more strict than `RFC 5961 section 5.2`_). | ||
660 | |||
661 | .. _RFC 5961 section 3.2: https://tools.ietf.org/html/rfc5961#page-7 | ||
662 | .. _RFC 5961 section 4.2: https://tools.ietf.org/html/rfc5961#page-9 | ||
663 | .. _RFC 5961 section 5.2: https://tools.ietf.org/html/rfc5961#page-11 | ||
664 | |||
575 | 665 | ||
576 | examples | 666 | examples |
577 | ======= | 667 | ======= |
@@ -1188,3 +1278,151 @@ Run nstat on server B:: | |||
1188 | We have deleted the default route on server B. Server B couldn't find | 1278 | We have deleted the default route on server B. Server B couldn't find |
1189 | a route for the 8.8.8.8 IP address, so server B increased | 1279 | a route for the 8.8.8.8 IP address, so server B increased |
1190 | IpOutNoRoutes. | 1280 | IpOutNoRoutes. |
1281 | |||
1282 | TcpExtTCPACKSkippedSynRecv | ||
1283 | ------------------------ | ||
1284 | In this test, we send 3 same SYN packets from client to server. The | ||
1285 | first SYN will let server create a socket, set it to Syn-Recv status, | ||
1286 | and reply a SYN/ACK. The second SYN will let server reply the SYN/ACK | ||
1287 | again, and record the reply time (the duplicate ACK reply time). The | ||
1288 | third SYN will let server check the previous duplicate ACK reply time, | ||
1289 | and decide to skip the duplicate ACK, then increase the | ||
1290 | TcpExtTCPACKSkippedSynRecv counter. | ||
1291 | |||
1292 | Run tcpdump to capture a SYN packet:: | ||
1293 | |||
1294 | nstatuser@nstat-a:~$ sudo tcpdump -c 1 -w /tmp/syn.pcap port 9000 | ||
1295 | tcpdump: listening on ens3, link-type EN10MB (Ethernet), capture size 262144 bytes | ||
1296 | |||
1297 | Open another terminal, run nc command:: | ||
1298 | |||
1299 | nstatuser@nstat-a:~$ nc nstat-b 9000 | ||
1300 | |||
1301 | As the nstat-b didn't listen on port 9000, it should reply a RST, and | ||
1302 | the nc command exited immediately. It was enough for the tcpdump | ||
1303 | command to capture a SYN packet. A linux server might use hardware | ||
1304 | offload for the TCP checksum, so the checksum in the /tmp/syn.pcap | ||
1305 | might be not correct. We call tcprewrite to fix it:: | ||
1306 | |||
1307 | nstatuser@nstat-a:~$ tcprewrite --infile=/tmp/syn.pcap --outfile=/tmp/syn_fixcsum.pcap --fixcsum | ||
1308 | |||
1309 | On nstat-b, we run nc to listen on port 9000:: | ||
1310 | |||
1311 | nstatuser@nstat-b:~$ nc -lkv 9000 | ||
1312 | Listening on [0.0.0.0] (family 0, port 9000) | ||
1313 | |||
1314 | On nstat-a, we blocked the packet from port 9000, or nstat-a would send | ||
1315 | RST to nstat-b:: | ||
1316 | |||
1317 | nstatuser@nstat-a:~$ sudo iptables -A INPUT -p tcp --sport 9000 -j DROP | ||
1318 | |||
1319 | Send 3 SYN repeatly to nstat-b:: | ||
1320 | |||
1321 | nstatuser@nstat-a:~$ for i in {1..3}; do sudo tcpreplay -i ens3 /tmp/syn_fixcsum.pcap; done | ||
1322 | |||
1323 | Check snmp cunter on nstat-b:: | ||
1324 | |||
1325 | nstatuser@nstat-b:~$ nstat | grep -i skip | ||
1326 | TcpExtTCPACKSkippedSynRecv 1 0.0 | ||
1327 | |||
1328 | As we expected, TcpExtTCPACKSkippedSynRecv is 1. | ||
1329 | |||
1330 | TcpExtTCPACKSkippedPAWS | ||
1331 | ---------------------- | ||
1332 | To trigger PAWS, we could send an old SYN. | ||
1333 | |||
1334 | On nstat-b, let nc listen on port 9000:: | ||
1335 | |||
1336 | nstatuser@nstat-b:~$ nc -lkv 9000 | ||
1337 | Listening on [0.0.0.0] (family 0, port 9000) | ||
1338 | |||
1339 | On nstat-a, run tcpdump to capture a SYN:: | ||
1340 | |||
1341 | nstatuser@nstat-a:~$ sudo tcpdump -w /tmp/paws_pre.pcap -c 1 port 9000 | ||
1342 | tcpdump: listening on ens3, link-type EN10MB (Ethernet), capture size 262144 bytes | ||
1343 | |||
1344 | On nstat-a, run nc as a client to connect nstat-b:: | ||
1345 | |||
1346 | nstatuser@nstat-a:~$ nc -v nstat-b 9000 | ||
1347 | Connection to nstat-b 9000 port [tcp/*] succeeded! | ||
1348 | |||
1349 | Now the tcpdump has captured the SYN and exit. We should fix the | ||
1350 | checksum:: | ||
1351 | |||
1352 | nstatuser@nstat-a:~$ tcprewrite --infile /tmp/paws_pre.pcap --outfile /tmp/paws.pcap --fixcsum | ||
1353 | |||
1354 | Send the SYN packet twice:: | ||
1355 | |||
1356 | nstatuser@nstat-a:~$ for i in {1..2}; do sudo tcpreplay -i ens3 /tmp/paws.pcap; done | ||
1357 | |||
1358 | On nstat-b, check the snmp counter:: | ||
1359 | |||
1360 | nstatuser@nstat-b:~$ nstat | grep -i skip | ||
1361 | TcpExtTCPACKSkippedPAWS 1 0.0 | ||
1362 | |||
1363 | We sent two SYN via tcpreplay, both of them would let PAWS check | ||
1364 | failed, the nstat-b replied an ACK for the first SYN, skipped the ACK | ||
1365 | for the second SYN, and updated TcpExtTCPACKSkippedPAWS. | ||
1366 | |||
1367 | TcpExtTCPACKSkippedSeq | ||
1368 | -------------------- | ||
1369 | To trigger TcpExtTCPACKSkippedSeq, we send packets which have valid | ||
1370 | timestamp (to pass PAWS check) but the sequence number is out of | ||
1371 | window. The linux TCP stack would avoid to skip if the packet has | ||
1372 | data, so we need a pure ACK packet. To generate such a packet, we | ||
1373 | could create two sockets: one on port 9000, another on port 9001. Then | ||
1374 | we capture an ACK on port 9001, change the source/destination port | ||
1375 | numbers to match the port 9000 socket. Then we could trigger | ||
1376 | TcpExtTCPACKSkippedSeq via this packet. | ||
1377 | |||
1378 | On nstat-b, open two terminals, run two nc commands to listen on both | ||
1379 | port 9000 and port 9001:: | ||
1380 | |||
1381 | nstatuser@nstat-b:~$ nc -lkv 9000 | ||
1382 | Listening on [0.0.0.0] (family 0, port 9000) | ||
1383 | |||
1384 | nstatuser@nstat-b:~$ nc -lkv 9001 | ||
1385 | Listening on [0.0.0.0] (family 0, port 9001) | ||
1386 | |||
1387 | On nstat-a, run two nc clients:: | ||
1388 | |||
1389 | nstatuser@nstat-a:~$ nc -v nstat-b 9000 | ||
1390 | Connection to nstat-b 9000 port [tcp/*] succeeded! | ||
1391 | |||
1392 | nstatuser@nstat-a:~$ nc -v nstat-b 9001 | ||
1393 | Connection to nstat-b 9001 port [tcp/*] succeeded! | ||
1394 | |||
1395 | On nstat-a, run tcpdump to capture an ACK:: | ||
1396 | |||
1397 | nstatuser@nstat-a:~$ sudo tcpdump -w /tmp/seq_pre.pcap -c 1 dst port 9001 | ||
1398 | tcpdump: listening on ens3, link-type EN10MB (Ethernet), capture size 262144 bytes | ||
1399 | |||
1400 | On nstat-b, send a packet via the port 9001 socket. E.g. we sent a | ||
1401 | string 'foo' in our example:: | ||
1402 | |||
1403 | nstatuser@nstat-b:~$ nc -lkv 9001 | ||
1404 | Listening on [0.0.0.0] (family 0, port 9001) | ||
1405 | Connection from nstat-a 42132 received! | ||
1406 | foo | ||
1407 | |||
1408 | On nstat-a, the tcpdump should have caputred the ACK. We should check | ||
1409 | the source port numbers of the two nc clients:: | ||
1410 | |||
1411 | nstatuser@nstat-a:~$ ss -ta '( dport = :9000 || dport = :9001 )' | tee | ||
1412 | State Recv-Q Send-Q Local Address:Port Peer Address:Port | ||
1413 | ESTAB 0 0 192.168.122.250:50208 192.168.122.251:9000 | ||
1414 | ESTAB 0 0 192.168.122.250:42132 192.168.122.251:9001 | ||
1415 | |||
1416 | Run tcprewrite, change port 9001 to port 9000, chagne port 42132 to | ||
1417 | port 50208:: | ||
1418 | |||
1419 | nstatuser@nstat-a:~$ tcprewrite --infile /tmp/seq_pre.pcap --outfile /tmp/seq.pcap -r 9001:9000 -r 42132:50208 --fixcsum | ||
1420 | |||
1421 | Now the /tmp/seq.pcap is the packet we need. Send it to nstat-b:: | ||
1422 | |||
1423 | nstatuser@nstat-a:~$ for i in {1..2}; do sudo tcpreplay -i ens3 /tmp/seq.pcap; done | ||
1424 | |||
1425 | Check TcpExtTCPACKSkippedSeq on nstat-b:: | ||
1426 | |||
1427 | nstatuser@nstat-b:~$ nstat | grep -i skip | ||
1428 | TcpExtTCPACKSkippedSeq 1 0.0 | ||
diff --git a/arch/alpha/include/asm/futex.h b/arch/alpha/include/asm/futex.h index ca3322536f72..bfd3c01038f8 100644 --- a/arch/alpha/include/asm/futex.h +++ b/arch/alpha/include/asm/futex.h | |||
@@ -68,7 +68,7 @@ futex_atomic_cmpxchg_inatomic(u32 *uval, u32 __user *uaddr, | |||
68 | int ret = 0, cmp; | 68 | int ret = 0, cmp; |
69 | u32 prev; | 69 | u32 prev; |
70 | 70 | ||
71 | if (!access_ok(VERIFY_WRITE, uaddr, sizeof(u32))) | 71 | if (!access_ok(uaddr, sizeof(u32))) |
72 | return -EFAULT; | 72 | return -EFAULT; |
73 | 73 | ||
74 | __asm__ __volatile__ ( | 74 | __asm__ __volatile__ ( |
diff --git a/arch/alpha/include/asm/uaccess.h b/arch/alpha/include/asm/uaccess.h index 87d8c4f0307d..e69c4e13c328 100644 --- a/arch/alpha/include/asm/uaccess.h +++ b/arch/alpha/include/asm/uaccess.h | |||
@@ -36,7 +36,7 @@ | |||
36 | #define __access_ok(addr, size) \ | 36 | #define __access_ok(addr, size) \ |
37 | ((get_fs().seg & (addr | size | (addr+size))) == 0) | 37 | ((get_fs().seg & (addr | size | (addr+size))) == 0) |
38 | 38 | ||
39 | #define access_ok(type, addr, size) \ | 39 | #define access_ok(addr, size) \ |
40 | ({ \ | 40 | ({ \ |
41 | __chk_user_ptr(addr); \ | 41 | __chk_user_ptr(addr); \ |
42 | __access_ok(((unsigned long)(addr)), (size)); \ | 42 | __access_ok(((unsigned long)(addr)), (size)); \ |
diff --git a/arch/alpha/kernel/signal.c b/arch/alpha/kernel/signal.c index 8c0c4ee0be6e..33e904a05881 100644 --- a/arch/alpha/kernel/signal.c +++ b/arch/alpha/kernel/signal.c | |||
@@ -65,7 +65,7 @@ SYSCALL_DEFINE3(osf_sigaction, int, sig, | |||
65 | 65 | ||
66 | if (act) { | 66 | if (act) { |
67 | old_sigset_t mask; | 67 | old_sigset_t mask; |
68 | if (!access_ok(VERIFY_READ, act, sizeof(*act)) || | 68 | if (!access_ok(act, sizeof(*act)) || |
69 | __get_user(new_ka.sa.sa_handler, &act->sa_handler) || | 69 | __get_user(new_ka.sa.sa_handler, &act->sa_handler) || |
70 | __get_user(new_ka.sa.sa_flags, &act->sa_flags) || | 70 | __get_user(new_ka.sa.sa_flags, &act->sa_flags) || |
71 | __get_user(mask, &act->sa_mask)) | 71 | __get_user(mask, &act->sa_mask)) |
@@ -77,7 +77,7 @@ SYSCALL_DEFINE3(osf_sigaction, int, sig, | |||
77 | ret = do_sigaction(sig, act ? &new_ka : NULL, oact ? &old_ka : NULL); | 77 | ret = do_sigaction(sig, act ? &new_ka : NULL, oact ? &old_ka : NULL); |
78 | 78 | ||
79 | if (!ret && oact) { | 79 | if (!ret && oact) { |
80 | if (!access_ok(VERIFY_WRITE, oact, sizeof(*oact)) || | 80 | if (!access_ok(oact, sizeof(*oact)) || |
81 | __put_user(old_ka.sa.sa_handler, &oact->sa_handler) || | 81 | __put_user(old_ka.sa.sa_handler, &oact->sa_handler) || |
82 | __put_user(old_ka.sa.sa_flags, &oact->sa_flags) || | 82 | __put_user(old_ka.sa.sa_flags, &oact->sa_flags) || |
83 | __put_user(old_ka.sa.sa_mask.sig[0], &oact->sa_mask)) | 83 | __put_user(old_ka.sa.sa_mask.sig[0], &oact->sa_mask)) |
@@ -207,7 +207,7 @@ do_sigreturn(struct sigcontext __user *sc) | |||
207 | sigset_t set; | 207 | sigset_t set; |
208 | 208 | ||
209 | /* Verify that it's a good sigcontext before using it */ | 209 | /* Verify that it's a good sigcontext before using it */ |
210 | if (!access_ok(VERIFY_READ, sc, sizeof(*sc))) | 210 | if (!access_ok(sc, sizeof(*sc))) |
211 | goto give_sigsegv; | 211 | goto give_sigsegv; |
212 | if (__get_user(set.sig[0], &sc->sc_mask)) | 212 | if (__get_user(set.sig[0], &sc->sc_mask)) |
213 | goto give_sigsegv; | 213 | goto give_sigsegv; |
@@ -235,7 +235,7 @@ do_rt_sigreturn(struct rt_sigframe __user *frame) | |||
235 | sigset_t set; | 235 | sigset_t set; |
236 | 236 | ||
237 | /* Verify that it's a good ucontext_t before using it */ | 237 | /* Verify that it's a good ucontext_t before using it */ |
238 | if (!access_ok(VERIFY_READ, &frame->uc, sizeof(frame->uc))) | 238 | if (!access_ok(&frame->uc, sizeof(frame->uc))) |
239 | goto give_sigsegv; | 239 | goto give_sigsegv; |
240 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) | 240 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) |
241 | goto give_sigsegv; | 241 | goto give_sigsegv; |
@@ -332,7 +332,7 @@ setup_frame(struct ksignal *ksig, sigset_t *set, struct pt_regs *regs) | |||
332 | 332 | ||
333 | oldsp = rdusp(); | 333 | oldsp = rdusp(); |
334 | frame = get_sigframe(ksig, oldsp, sizeof(*frame)); | 334 | frame = get_sigframe(ksig, oldsp, sizeof(*frame)); |
335 | if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame))) | 335 | if (!access_ok(frame, sizeof(*frame))) |
336 | return -EFAULT; | 336 | return -EFAULT; |
337 | 337 | ||
338 | err |= setup_sigcontext(&frame->sc, regs, set->sig[0], oldsp); | 338 | err |= setup_sigcontext(&frame->sc, regs, set->sig[0], oldsp); |
@@ -377,7 +377,7 @@ setup_rt_frame(struct ksignal *ksig, sigset_t *set, struct pt_regs *regs) | |||
377 | 377 | ||
378 | oldsp = rdusp(); | 378 | oldsp = rdusp(); |
379 | frame = get_sigframe(ksig, oldsp, sizeof(*frame)); | 379 | frame = get_sigframe(ksig, oldsp, sizeof(*frame)); |
380 | if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame))) | 380 | if (!access_ok(frame, sizeof(*frame))) |
381 | return -EFAULT; | 381 | return -EFAULT; |
382 | 382 | ||
383 | err |= copy_siginfo_to_user(&frame->info, &ksig->info); | 383 | err |= copy_siginfo_to_user(&frame->info, &ksig->info); |
diff --git a/arch/alpha/lib/csum_partial_copy.c b/arch/alpha/lib/csum_partial_copy.c index ddb9c2f376fa..e53f96e8aa6d 100644 --- a/arch/alpha/lib/csum_partial_copy.c +++ b/arch/alpha/lib/csum_partial_copy.c | |||
@@ -333,7 +333,7 @@ csum_partial_copy_from_user(const void __user *src, void *dst, int len, | |||
333 | unsigned long doff = 7 & (unsigned long) dst; | 333 | unsigned long doff = 7 & (unsigned long) dst; |
334 | 334 | ||
335 | if (len) { | 335 | if (len) { |
336 | if (!access_ok(VERIFY_READ, src, len)) { | 336 | if (!access_ok(src, len)) { |
337 | if (errp) *errp = -EFAULT; | 337 | if (errp) *errp = -EFAULT; |
338 | memset(dst, 0, len); | 338 | memset(dst, 0, len); |
339 | return sum; | 339 | return sum; |
diff --git a/arch/arc/include/asm/futex.h b/arch/arc/include/asm/futex.h index eb887dd13e74..c29c3fae6854 100644 --- a/arch/arc/include/asm/futex.h +++ b/arch/arc/include/asm/futex.h | |||
@@ -126,7 +126,7 @@ futex_atomic_cmpxchg_inatomic(u32 *uval, u32 __user *uaddr, u32 expval, | |||
126 | int ret = 0; | 126 | int ret = 0; |
127 | u32 existval; | 127 | u32 existval; |
128 | 128 | ||
129 | if (!access_ok(VERIFY_WRITE, uaddr, sizeof(u32))) | 129 | if (!access_ok(uaddr, sizeof(u32))) |
130 | return -EFAULT; | 130 | return -EFAULT; |
131 | 131 | ||
132 | #ifndef CONFIG_ARC_HAS_LLSC | 132 | #ifndef CONFIG_ARC_HAS_LLSC |
diff --git a/arch/arc/kernel/process.c b/arch/arc/kernel/process.c index 8ce6e7235915..641c364fc232 100644 --- a/arch/arc/kernel/process.c +++ b/arch/arc/kernel/process.c | |||
@@ -61,7 +61,7 @@ SYSCALL_DEFINE3(arc_usr_cmpxchg, int *, uaddr, int, expected, int, new) | |||
61 | /* Z indicates to userspace if operation succeded */ | 61 | /* Z indicates to userspace if operation succeded */ |
62 | regs->status32 &= ~STATUS_Z_MASK; | 62 | regs->status32 &= ~STATUS_Z_MASK; |
63 | 63 | ||
64 | ret = access_ok(VERIFY_WRITE, uaddr, sizeof(*uaddr)); | 64 | ret = access_ok(uaddr, sizeof(*uaddr)); |
65 | if (!ret) | 65 | if (!ret) |
66 | goto fail; | 66 | goto fail; |
67 | 67 | ||
diff --git a/arch/arc/kernel/signal.c b/arch/arc/kernel/signal.c index 48685445002e..1bfb7de696bd 100644 --- a/arch/arc/kernel/signal.c +++ b/arch/arc/kernel/signal.c | |||
@@ -169,7 +169,7 @@ SYSCALL_DEFINE0(rt_sigreturn) | |||
169 | 169 | ||
170 | sf = (struct rt_sigframe __force __user *)(regs->sp); | 170 | sf = (struct rt_sigframe __force __user *)(regs->sp); |
171 | 171 | ||
172 | if (!access_ok(VERIFY_READ, sf, sizeof(*sf))) | 172 | if (!access_ok(sf, sizeof(*sf))) |
173 | goto badframe; | 173 | goto badframe; |
174 | 174 | ||
175 | if (__get_user(magic, &sf->sigret_magic)) | 175 | if (__get_user(magic, &sf->sigret_magic)) |
@@ -219,7 +219,7 @@ static inline void __user *get_sigframe(struct ksignal *ksig, | |||
219 | frame = (void __user *)((sp - framesize) & ~7); | 219 | frame = (void __user *)((sp - framesize) & ~7); |
220 | 220 | ||
221 | /* Check that we can actually write to the signal frame */ | 221 | /* Check that we can actually write to the signal frame */ |
222 | if (!access_ok(VERIFY_WRITE, frame, framesize)) | 222 | if (!access_ok(frame, framesize)) |
223 | frame = NULL; | 223 | frame = NULL; |
224 | 224 | ||
225 | return frame; | 225 | return frame; |
diff --git a/arch/arm/include/asm/futex.h b/arch/arm/include/asm/futex.h index ffebe7b7a5b7..0a46676b4245 100644 --- a/arch/arm/include/asm/futex.h +++ b/arch/arm/include/asm/futex.h | |||
@@ -50,7 +50,7 @@ futex_atomic_cmpxchg_inatomic(u32 *uval, u32 __user *uaddr, | |||
50 | int ret; | 50 | int ret; |
51 | u32 val; | 51 | u32 val; |
52 | 52 | ||
53 | if (!access_ok(VERIFY_WRITE, uaddr, sizeof(u32))) | 53 | if (!access_ok(uaddr, sizeof(u32))) |
54 | return -EFAULT; | 54 | return -EFAULT; |
55 | 55 | ||
56 | smp_mb(); | 56 | smp_mb(); |
@@ -104,7 +104,7 @@ futex_atomic_cmpxchg_inatomic(u32 *uval, u32 __user *uaddr, | |||
104 | int ret = 0; | 104 | int ret = 0; |
105 | u32 val; | 105 | u32 val; |
106 | 106 | ||
107 | if (!access_ok(VERIFY_WRITE, uaddr, sizeof(u32))) | 107 | if (!access_ok(uaddr, sizeof(u32))) |
108 | return -EFAULT; | 108 | return -EFAULT; |
109 | 109 | ||
110 | preempt_disable(); | 110 | preempt_disable(); |
diff --git a/arch/arm/include/asm/uaccess.h b/arch/arm/include/asm/uaccess.h index c136eef8f690..27ed17ec45fe 100644 --- a/arch/arm/include/asm/uaccess.h +++ b/arch/arm/include/asm/uaccess.h | |||
@@ -279,7 +279,7 @@ static inline void set_fs(mm_segment_t fs) | |||
279 | 279 | ||
280 | #endif /* CONFIG_MMU */ | 280 | #endif /* CONFIG_MMU */ |
281 | 281 | ||
282 | #define access_ok(type, addr, size) (__range_ok(addr, size) == 0) | 282 | #define access_ok(addr, size) (__range_ok(addr, size) == 0) |
283 | 283 | ||
284 | #define user_addr_max() \ | 284 | #define user_addr_max() \ |
285 | (uaccess_kernel() ? ~0UL : get_fs()) | 285 | (uaccess_kernel() ? ~0UL : get_fs()) |
@@ -560,7 +560,7 @@ raw_copy_to_user(void __user *to, const void *from, unsigned long n) | |||
560 | 560 | ||
561 | static inline unsigned long __must_check clear_user(void __user *to, unsigned long n) | 561 | static inline unsigned long __must_check clear_user(void __user *to, unsigned long n) |
562 | { | 562 | { |
563 | if (access_ok(VERIFY_WRITE, to, n)) | 563 | if (access_ok(to, n)) |
564 | n = __clear_user(to, n); | 564 | n = __clear_user(to, n); |
565 | return n; | 565 | return n; |
566 | } | 566 | } |
diff --git a/arch/arm/kernel/perf_callchain.c b/arch/arm/kernel/perf_callchain.c index 08e43a32a693..3b69a76d341e 100644 --- a/arch/arm/kernel/perf_callchain.c +++ b/arch/arm/kernel/perf_callchain.c | |||
@@ -37,7 +37,7 @@ user_backtrace(struct frame_tail __user *tail, | |||
37 | struct frame_tail buftail; | 37 | struct frame_tail buftail; |
38 | unsigned long err; | 38 | unsigned long err; |
39 | 39 | ||
40 | if (!access_ok(VERIFY_READ, tail, sizeof(buftail))) | 40 | if (!access_ok(tail, sizeof(buftail))) |
41 | return NULL; | 41 | return NULL; |
42 | 42 | ||
43 | pagefault_disable(); | 43 | pagefault_disable(); |
diff --git a/arch/arm/kernel/signal.c b/arch/arm/kernel/signal.c index b908382b69ff..76bb8de6bf6b 100644 --- a/arch/arm/kernel/signal.c +++ b/arch/arm/kernel/signal.c | |||
@@ -241,7 +241,7 @@ asmlinkage int sys_sigreturn(struct pt_regs *regs) | |||
241 | 241 | ||
242 | frame = (struct sigframe __user *)regs->ARM_sp; | 242 | frame = (struct sigframe __user *)regs->ARM_sp; |
243 | 243 | ||
244 | if (!access_ok(VERIFY_READ, frame, sizeof (*frame))) | 244 | if (!access_ok(frame, sizeof (*frame))) |
245 | goto badframe; | 245 | goto badframe; |
246 | 246 | ||
247 | if (restore_sigframe(regs, frame)) | 247 | if (restore_sigframe(regs, frame)) |
@@ -271,7 +271,7 @@ asmlinkage int sys_rt_sigreturn(struct pt_regs *regs) | |||
271 | 271 | ||
272 | frame = (struct rt_sigframe __user *)regs->ARM_sp; | 272 | frame = (struct rt_sigframe __user *)regs->ARM_sp; |
273 | 273 | ||
274 | if (!access_ok(VERIFY_READ, frame, sizeof (*frame))) | 274 | if (!access_ok(frame, sizeof (*frame))) |
275 | goto badframe; | 275 | goto badframe; |
276 | 276 | ||
277 | if (restore_sigframe(regs, &frame->sig)) | 277 | if (restore_sigframe(regs, &frame->sig)) |
@@ -355,7 +355,7 @@ get_sigframe(struct ksignal *ksig, struct pt_regs *regs, int framesize) | |||
355 | /* | 355 | /* |
356 | * Check that we can actually write to the signal frame. | 356 | * Check that we can actually write to the signal frame. |
357 | */ | 357 | */ |
358 | if (!access_ok(VERIFY_WRITE, frame, framesize)) | 358 | if (!access_ok(frame, framesize)) |
359 | frame = NULL; | 359 | frame = NULL; |
360 | 360 | ||
361 | return frame; | 361 | return frame; |
diff --git a/arch/arm/kernel/swp_emulate.c b/arch/arm/kernel/swp_emulate.c index a188d5e8ab7f..76f6e6a9736c 100644 --- a/arch/arm/kernel/swp_emulate.c +++ b/arch/arm/kernel/swp_emulate.c | |||
@@ -198,7 +198,7 @@ static int swp_handler(struct pt_regs *regs, unsigned int instr) | |||
198 | destreg, EXTRACT_REG_NUM(instr, RT2_OFFSET), data); | 198 | destreg, EXTRACT_REG_NUM(instr, RT2_OFFSET), data); |
199 | 199 | ||
200 | /* Check access in reasonable access range for both SWP and SWPB */ | 200 | /* Check access in reasonable access range for both SWP and SWPB */ |
201 | if (!access_ok(VERIFY_WRITE, (address & ~3), 4)) { | 201 | if (!access_ok((address & ~3), 4)) { |
202 | pr_debug("SWP{B} emulation: access to %p not allowed!\n", | 202 | pr_debug("SWP{B} emulation: access to %p not allowed!\n", |
203 | (void *)address); | 203 | (void *)address); |
204 | res = -EFAULT; | 204 | res = -EFAULT; |
diff --git a/arch/arm/kernel/sys_oabi-compat.c b/arch/arm/kernel/sys_oabi-compat.c index 40da0872170f..92ab36f38795 100644 --- a/arch/arm/kernel/sys_oabi-compat.c +++ b/arch/arm/kernel/sys_oabi-compat.c | |||
@@ -285,7 +285,7 @@ asmlinkage long sys_oabi_epoll_wait(int epfd, | |||
285 | maxevents > (INT_MAX/sizeof(*kbuf)) || | 285 | maxevents > (INT_MAX/sizeof(*kbuf)) || |
286 | maxevents > (INT_MAX/sizeof(*events))) | 286 | maxevents > (INT_MAX/sizeof(*events))) |
287 | return -EINVAL; | 287 | return -EINVAL; |
288 | if (!access_ok(VERIFY_WRITE, events, sizeof(*events) * maxevents)) | 288 | if (!access_ok(events, sizeof(*events) * maxevents)) |
289 | return -EFAULT; | 289 | return -EFAULT; |
290 | kbuf = kmalloc_array(maxevents, sizeof(*kbuf), GFP_KERNEL); | 290 | kbuf = kmalloc_array(maxevents, sizeof(*kbuf), GFP_KERNEL); |
291 | if (!kbuf) | 291 | if (!kbuf) |
@@ -326,7 +326,7 @@ asmlinkage long sys_oabi_semtimedop(int semid, | |||
326 | 326 | ||
327 | if (nsops < 1 || nsops > SEMOPM) | 327 | if (nsops < 1 || nsops > SEMOPM) |
328 | return -EINVAL; | 328 | return -EINVAL; |
329 | if (!access_ok(VERIFY_READ, tsops, sizeof(*tsops) * nsops)) | 329 | if (!access_ok(tsops, sizeof(*tsops) * nsops)) |
330 | return -EFAULT; | 330 | return -EFAULT; |
331 | sops = kmalloc_array(nsops, sizeof(*sops), GFP_KERNEL); | 331 | sops = kmalloc_array(nsops, sizeof(*sops), GFP_KERNEL); |
332 | if (!sops) | 332 | if (!sops) |
diff --git a/arch/arm/kernel/traps.c b/arch/arm/kernel/traps.c index 2d668cff8ef4..33af097c454b 100644 --- a/arch/arm/kernel/traps.c +++ b/arch/arm/kernel/traps.c | |||
@@ -582,7 +582,7 @@ do_cache_op(unsigned long start, unsigned long end, int flags) | |||
582 | if (end < start || flags) | 582 | if (end < start || flags) |
583 | return -EINVAL; | 583 | return -EINVAL; |
584 | 584 | ||
585 | if (!access_ok(VERIFY_READ, start, end - start)) | 585 | if (!access_ok(start, end - start)) |
586 | return -EFAULT; | 586 | return -EFAULT; |
587 | 587 | ||
588 | return __do_cache_op(start, end); | 588 | return __do_cache_op(start, end); |
diff --git a/arch/arm/oprofile/common.c b/arch/arm/oprofile/common.c index cc649a1e46da..7cb3e0453fcd 100644 --- a/arch/arm/oprofile/common.c +++ b/arch/arm/oprofile/common.c | |||
@@ -88,7 +88,7 @@ static struct frame_tail* user_backtrace(struct frame_tail *tail) | |||
88 | struct frame_tail buftail[2]; | 88 | struct frame_tail buftail[2]; |
89 | 89 | ||
90 | /* Also check accessibility of one struct frame_tail beyond */ | 90 | /* Also check accessibility of one struct frame_tail beyond */ |
91 | if (!access_ok(VERIFY_READ, tail, sizeof(buftail))) | 91 | if (!access_ok(tail, sizeof(buftail))) |
92 | return NULL; | 92 | return NULL; |
93 | if (__copy_from_user_inatomic(buftail, tail, sizeof(buftail))) | 93 | if (__copy_from_user_inatomic(buftail, tail, sizeof(buftail))) |
94 | return NULL; | 94 | return NULL; |
diff --git a/arch/arm64/include/asm/futex.h b/arch/arm64/include/asm/futex.h index 07fe2479d310..cccb83ad7fa8 100644 --- a/arch/arm64/include/asm/futex.h +++ b/arch/arm64/include/asm/futex.h | |||
@@ -96,7 +96,7 @@ futex_atomic_cmpxchg_inatomic(u32 *uval, u32 __user *_uaddr, | |||
96 | u32 val, tmp; | 96 | u32 val, tmp; |
97 | u32 __user *uaddr; | 97 | u32 __user *uaddr; |
98 | 98 | ||
99 | if (!access_ok(VERIFY_WRITE, _uaddr, sizeof(u32))) | 99 | if (!access_ok(_uaddr, sizeof(u32))) |
100 | return -EFAULT; | 100 | return -EFAULT; |
101 | 101 | ||
102 | uaddr = __uaccess_mask_ptr(_uaddr); | 102 | uaddr = __uaccess_mask_ptr(_uaddr); |
diff --git a/arch/arm64/include/asm/uaccess.h b/arch/arm64/include/asm/uaccess.h index ed252435fd92..547d7a0c9d05 100644 --- a/arch/arm64/include/asm/uaccess.h +++ b/arch/arm64/include/asm/uaccess.h | |||
@@ -95,7 +95,7 @@ static inline unsigned long __range_ok(const void __user *addr, unsigned long si | |||
95 | return ret; | 95 | return ret; |
96 | } | 96 | } |
97 | 97 | ||
98 | #define access_ok(type, addr, size) __range_ok(addr, size) | 98 | #define access_ok(addr, size) __range_ok(addr, size) |
99 | #define user_addr_max get_fs | 99 | #define user_addr_max get_fs |
100 | 100 | ||
101 | #define _ASM_EXTABLE(from, to) \ | 101 | #define _ASM_EXTABLE(from, to) \ |
@@ -301,7 +301,7 @@ do { \ | |||
301 | ({ \ | 301 | ({ \ |
302 | __typeof__(*(ptr)) __user *__p = (ptr); \ | 302 | __typeof__(*(ptr)) __user *__p = (ptr); \ |
303 | might_fault(); \ | 303 | might_fault(); \ |
304 | if (access_ok(VERIFY_READ, __p, sizeof(*__p))) { \ | 304 | if (access_ok(__p, sizeof(*__p))) { \ |
305 | __p = uaccess_mask_ptr(__p); \ | 305 | __p = uaccess_mask_ptr(__p); \ |
306 | __get_user_err((x), __p, (err)); \ | 306 | __get_user_err((x), __p, (err)); \ |
307 | } else { \ | 307 | } else { \ |
@@ -370,7 +370,7 @@ do { \ | |||
370 | ({ \ | 370 | ({ \ |
371 | __typeof__(*(ptr)) __user *__p = (ptr); \ | 371 | __typeof__(*(ptr)) __user *__p = (ptr); \ |
372 | might_fault(); \ | 372 | might_fault(); \ |
373 | if (access_ok(VERIFY_WRITE, __p, sizeof(*__p))) { \ | 373 | if (access_ok(__p, sizeof(*__p))) { \ |
374 | __p = uaccess_mask_ptr(__p); \ | 374 | __p = uaccess_mask_ptr(__p); \ |
375 | __put_user_err((x), __p, (err)); \ | 375 | __put_user_err((x), __p, (err)); \ |
376 | } else { \ | 376 | } else { \ |
@@ -418,7 +418,7 @@ extern unsigned long __must_check __arch_copy_in_user(void __user *to, const voi | |||
418 | extern unsigned long __must_check __arch_clear_user(void __user *to, unsigned long n); | 418 | extern unsigned long __must_check __arch_clear_user(void __user *to, unsigned long n); |
419 | static inline unsigned long __must_check __clear_user(void __user *to, unsigned long n) | 419 | static inline unsigned long __must_check __clear_user(void __user *to, unsigned long n) |
420 | { | 420 | { |
421 | if (access_ok(VERIFY_WRITE, to, n)) | 421 | if (access_ok(to, n)) |
422 | n = __arch_clear_user(__uaccess_mask_ptr(to), n); | 422 | n = __arch_clear_user(__uaccess_mask_ptr(to), n); |
423 | return n; | 423 | return n; |
424 | } | 424 | } |
diff --git a/arch/arm64/kernel/armv8_deprecated.c b/arch/arm64/kernel/armv8_deprecated.c index 92be1d12d590..e52e7280884a 100644 --- a/arch/arm64/kernel/armv8_deprecated.c +++ b/arch/arm64/kernel/armv8_deprecated.c | |||
@@ -402,7 +402,7 @@ static int swp_handler(struct pt_regs *regs, u32 instr) | |||
402 | 402 | ||
403 | /* Check access in reasonable access range for both SWP and SWPB */ | 403 | /* Check access in reasonable access range for both SWP and SWPB */ |
404 | user_ptr = (const void __user *)(unsigned long)(address & ~3); | 404 | user_ptr = (const void __user *)(unsigned long)(address & ~3); |
405 | if (!access_ok(VERIFY_WRITE, user_ptr, 4)) { | 405 | if (!access_ok(user_ptr, 4)) { |
406 | pr_debug("SWP{B} emulation: access to 0x%08x not allowed!\n", | 406 | pr_debug("SWP{B} emulation: access to 0x%08x not allowed!\n", |
407 | address); | 407 | address); |
408 | goto fault; | 408 | goto fault; |
diff --git a/arch/arm64/kernel/perf_callchain.c b/arch/arm64/kernel/perf_callchain.c index a34c26afacb0..61d983f5756f 100644 --- a/arch/arm64/kernel/perf_callchain.c +++ b/arch/arm64/kernel/perf_callchain.c | |||
@@ -39,7 +39,7 @@ user_backtrace(struct frame_tail __user *tail, | |||
39 | unsigned long lr; | 39 | unsigned long lr; |
40 | 40 | ||
41 | /* Also check accessibility of one struct frame_tail beyond */ | 41 | /* Also check accessibility of one struct frame_tail beyond */ |
42 | if (!access_ok(VERIFY_READ, tail, sizeof(buftail))) | 42 | if (!access_ok(tail, sizeof(buftail))) |
43 | return NULL; | 43 | return NULL; |
44 | 44 | ||
45 | pagefault_disable(); | 45 | pagefault_disable(); |
@@ -86,7 +86,7 @@ compat_user_backtrace(struct compat_frame_tail __user *tail, | |||
86 | unsigned long err; | 86 | unsigned long err; |
87 | 87 | ||
88 | /* Also check accessibility of one struct frame_tail beyond */ | 88 | /* Also check accessibility of one struct frame_tail beyond */ |
89 | if (!access_ok(VERIFY_READ, tail, sizeof(buftail))) | 89 | if (!access_ok(tail, sizeof(buftail))) |
90 | return NULL; | 90 | return NULL; |
91 | 91 | ||
92 | pagefault_disable(); | 92 | pagefault_disable(); |
diff --git a/arch/arm64/kernel/signal.c b/arch/arm64/kernel/signal.c index 5dcc942906db..867a7cea70e5 100644 --- a/arch/arm64/kernel/signal.c +++ b/arch/arm64/kernel/signal.c | |||
@@ -470,7 +470,7 @@ static int parse_user_sigframe(struct user_ctxs *user, | |||
470 | offset = 0; | 470 | offset = 0; |
471 | limit = extra_size; | 471 | limit = extra_size; |
472 | 472 | ||
473 | if (!access_ok(VERIFY_READ, base, limit)) | 473 | if (!access_ok(base, limit)) |
474 | goto invalid; | 474 | goto invalid; |
475 | 475 | ||
476 | continue; | 476 | continue; |
@@ -556,7 +556,7 @@ SYSCALL_DEFINE0(rt_sigreturn) | |||
556 | 556 | ||
557 | frame = (struct rt_sigframe __user *)regs->sp; | 557 | frame = (struct rt_sigframe __user *)regs->sp; |
558 | 558 | ||
559 | if (!access_ok(VERIFY_READ, frame, sizeof (*frame))) | 559 | if (!access_ok(frame, sizeof (*frame))) |
560 | goto badframe; | 560 | goto badframe; |
561 | 561 | ||
562 | if (restore_sigframe(regs, frame)) | 562 | if (restore_sigframe(regs, frame)) |
@@ -730,7 +730,7 @@ static int get_sigframe(struct rt_sigframe_user_layout *user, | |||
730 | /* | 730 | /* |
731 | * Check that we can actually write to the signal frame. | 731 | * Check that we can actually write to the signal frame. |
732 | */ | 732 | */ |
733 | if (!access_ok(VERIFY_WRITE, user->sigframe, sp_top - sp)) | 733 | if (!access_ok(user->sigframe, sp_top - sp)) |
734 | return -EFAULT; | 734 | return -EFAULT; |
735 | 735 | ||
736 | return 0; | 736 | return 0; |
diff --git a/arch/arm64/kernel/signal32.c b/arch/arm64/kernel/signal32.c index 24b09003f821..cb7800acd19f 100644 --- a/arch/arm64/kernel/signal32.c +++ b/arch/arm64/kernel/signal32.c | |||
@@ -303,7 +303,7 @@ COMPAT_SYSCALL_DEFINE0(sigreturn) | |||
303 | 303 | ||
304 | frame = (struct compat_sigframe __user *)regs->compat_sp; | 304 | frame = (struct compat_sigframe __user *)regs->compat_sp; |
305 | 305 | ||
306 | if (!access_ok(VERIFY_READ, frame, sizeof (*frame))) | 306 | if (!access_ok(frame, sizeof (*frame))) |
307 | goto badframe; | 307 | goto badframe; |
308 | 308 | ||
309 | if (compat_restore_sigframe(regs, frame)) | 309 | if (compat_restore_sigframe(regs, frame)) |
@@ -334,7 +334,7 @@ COMPAT_SYSCALL_DEFINE0(rt_sigreturn) | |||
334 | 334 | ||
335 | frame = (struct compat_rt_sigframe __user *)regs->compat_sp; | 335 | frame = (struct compat_rt_sigframe __user *)regs->compat_sp; |
336 | 336 | ||
337 | if (!access_ok(VERIFY_READ, frame, sizeof (*frame))) | 337 | if (!access_ok(frame, sizeof (*frame))) |
338 | goto badframe; | 338 | goto badframe; |
339 | 339 | ||
340 | if (compat_restore_sigframe(regs, &frame->sig)) | 340 | if (compat_restore_sigframe(regs, &frame->sig)) |
@@ -365,7 +365,7 @@ static void __user *compat_get_sigframe(struct ksignal *ksig, | |||
365 | /* | 365 | /* |
366 | * Check that we can actually write to the signal frame. | 366 | * Check that we can actually write to the signal frame. |
367 | */ | 367 | */ |
368 | if (!access_ok(VERIFY_WRITE, frame, framesize)) | 368 | if (!access_ok(frame, framesize)) |
369 | frame = NULL; | 369 | frame = NULL; |
370 | 370 | ||
371 | return frame; | 371 | return frame; |
diff --git a/arch/arm64/kernel/sys_compat.c b/arch/arm64/kernel/sys_compat.c index 32653d156747..21005dfe8406 100644 --- a/arch/arm64/kernel/sys_compat.c +++ b/arch/arm64/kernel/sys_compat.c | |||
@@ -58,7 +58,7 @@ do_compat_cache_op(unsigned long start, unsigned long end, int flags) | |||
58 | if (end < start || flags) | 58 | if (end < start || flags) |
59 | return -EINVAL; | 59 | return -EINVAL; |
60 | 60 | ||
61 | if (!access_ok(VERIFY_READ, (const void __user *)start, end - start)) | 61 | if (!access_ok((const void __user *)start, end - start)) |
62 | return -EFAULT; | 62 | return -EFAULT; |
63 | 63 | ||
64 | return __do_compat_cache_op(start, end); | 64 | return __do_compat_cache_op(start, end); |
diff --git a/arch/c6x/kernel/signal.c b/arch/c6x/kernel/signal.c index 3c4bb5a5c382..33b9f69c38f7 100644 --- a/arch/c6x/kernel/signal.c +++ b/arch/c6x/kernel/signal.c | |||
@@ -80,7 +80,7 @@ asmlinkage int do_rt_sigreturn(struct pt_regs *regs) | |||
80 | 80 | ||
81 | frame = (struct rt_sigframe __user *) ((unsigned long) regs->sp + 8); | 81 | frame = (struct rt_sigframe __user *) ((unsigned long) regs->sp + 8); |
82 | 82 | ||
83 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 83 | if (!access_ok(frame, sizeof(*frame))) |
84 | goto badframe; | 84 | goto badframe; |
85 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) | 85 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) |
86 | goto badframe; | 86 | goto badframe; |
@@ -149,7 +149,7 @@ static int setup_rt_frame(struct ksignal *ksig, sigset_t *set, | |||
149 | 149 | ||
150 | frame = get_sigframe(ksig, regs, sizeof(*frame)); | 150 | frame = get_sigframe(ksig, regs, sizeof(*frame)); |
151 | 151 | ||
152 | if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame))) | 152 | if (!access_ok(frame, sizeof(*frame))) |
153 | return -EFAULT; | 153 | return -EFAULT; |
154 | 154 | ||
155 | err |= __put_user(&frame->info, &frame->pinfo); | 155 | err |= __put_user(&frame->info, &frame->pinfo); |
diff --git a/arch/csky/abiv1/alignment.c b/arch/csky/abiv1/alignment.c index 60205e98fb87..d789be36eb4f 100644 --- a/arch/csky/abiv1/alignment.c +++ b/arch/csky/abiv1/alignment.c | |||
@@ -32,7 +32,7 @@ static int ldb_asm(uint32_t addr, uint32_t *valp) | |||
32 | uint32_t val; | 32 | uint32_t val; |
33 | int err; | 33 | int err; |
34 | 34 | ||
35 | if (!access_ok(VERIFY_READ, (void *)addr, 1)) | 35 | if (!access_ok((void *)addr, 1)) |
36 | return 1; | 36 | return 1; |
37 | 37 | ||
38 | asm volatile ( | 38 | asm volatile ( |
@@ -67,7 +67,7 @@ static int stb_asm(uint32_t addr, uint32_t val) | |||
67 | { | 67 | { |
68 | int err; | 68 | int err; |
69 | 69 | ||
70 | if (!access_ok(VERIFY_WRITE, (void *)addr, 1)) | 70 | if (!access_ok((void *)addr, 1)) |
71 | return 1; | 71 | return 1; |
72 | 72 | ||
73 | asm volatile ( | 73 | asm volatile ( |
diff --git a/arch/csky/include/asm/uaccess.h b/arch/csky/include/asm/uaccess.h index acaf0e210d81..eaa1c3403a42 100644 --- a/arch/csky/include/asm/uaccess.h +++ b/arch/csky/include/asm/uaccess.h | |||
@@ -16,10 +16,7 @@ | |||
16 | #include <linux/version.h> | 16 | #include <linux/version.h> |
17 | #include <asm/segment.h> | 17 | #include <asm/segment.h> |
18 | 18 | ||
19 | #define VERIFY_READ 0 | 19 | static inline int access_ok(const void *addr, unsigned long size) |
20 | #define VERIFY_WRITE 1 | ||
21 | |||
22 | static inline int access_ok(int type, const void *addr, unsigned long size) | ||
23 | { | 20 | { |
24 | unsigned long limit = current_thread_info()->addr_limit.seg; | 21 | unsigned long limit = current_thread_info()->addr_limit.seg; |
25 | 22 | ||
@@ -27,12 +24,7 @@ static inline int access_ok(int type, const void *addr, unsigned long size) | |||
27 | ((unsigned long)(addr + size) < limit)); | 24 | ((unsigned long)(addr + size) < limit)); |
28 | } | 25 | } |
29 | 26 | ||
30 | static inline int verify_area(int type, const void *addr, unsigned long size) | 27 | #define __addr_ok(addr) (access_ok(addr, 0)) |
31 | { | ||
32 | return access_ok(type, addr, size) ? 0 : -EFAULT; | ||
33 | } | ||
34 | |||
35 | #define __addr_ok(addr) (access_ok(VERIFY_READ, addr, 0)) | ||
36 | 28 | ||
37 | extern int __put_user_bad(void); | 29 | extern int __put_user_bad(void); |
38 | 30 | ||
@@ -91,7 +83,7 @@ extern int __put_user_bad(void); | |||
91 | long __pu_err = -EFAULT; \ | 83 | long __pu_err = -EFAULT; \ |
92 | typeof(*(ptr)) *__pu_addr = (ptr); \ | 84 | typeof(*(ptr)) *__pu_addr = (ptr); \ |
93 | typeof(*(ptr)) __pu_val = (typeof(*(ptr)))(x); \ | 85 | typeof(*(ptr)) __pu_val = (typeof(*(ptr)))(x); \ |
94 | if (access_ok(VERIFY_WRITE, __pu_addr, size) && __pu_addr) \ | 86 | if (access_ok(__pu_addr, size) && __pu_addr) \ |
95 | __put_user_size(__pu_val, __pu_addr, (size), __pu_err); \ | 87 | __put_user_size(__pu_val, __pu_addr, (size), __pu_err); \ |
96 | __pu_err; \ | 88 | __pu_err; \ |
97 | }) | 89 | }) |
@@ -217,7 +209,7 @@ do { \ | |||
217 | ({ \ | 209 | ({ \ |
218 | int __gu_err = -EFAULT; \ | 210 | int __gu_err = -EFAULT; \ |
219 | const __typeof__(*(ptr)) __user *__gu_ptr = (ptr); \ | 211 | const __typeof__(*(ptr)) __user *__gu_ptr = (ptr); \ |
220 | if (access_ok(VERIFY_READ, __gu_ptr, size) && __gu_ptr) \ | 212 | if (access_ok(__gu_ptr, size) && __gu_ptr) \ |
221 | __get_user_size(x, __gu_ptr, size, __gu_err); \ | 213 | __get_user_size(x, __gu_ptr, size, __gu_err); \ |
222 | __gu_err; \ | 214 | __gu_err; \ |
223 | }) | 215 | }) |
diff --git a/arch/csky/kernel/signal.c b/arch/csky/kernel/signal.c index 66e1b729b10b..9967c10eee2b 100644 --- a/arch/csky/kernel/signal.c +++ b/arch/csky/kernel/signal.c | |||
@@ -88,7 +88,7 @@ do_rt_sigreturn(void) | |||
88 | struct pt_regs *regs = current_pt_regs(); | 88 | struct pt_regs *regs = current_pt_regs(); |
89 | struct rt_sigframe *frame = (struct rt_sigframe *)(regs->usp); | 89 | struct rt_sigframe *frame = (struct rt_sigframe *)(regs->usp); |
90 | 90 | ||
91 | if (verify_area(VERIFY_READ, frame, sizeof(*frame))) | 91 | if (!access_ok(frame, sizeof(*frame))) |
92 | goto badframe; | 92 | goto badframe; |
93 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) | 93 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) |
94 | goto badframe; | 94 | goto badframe; |
diff --git a/arch/csky/lib/usercopy.c b/arch/csky/lib/usercopy.c index ac9170e2cbb8..647a23986fb5 100644 --- a/arch/csky/lib/usercopy.c +++ b/arch/csky/lib/usercopy.c | |||
@@ -7,7 +7,7 @@ | |||
7 | unsigned long raw_copy_from_user(void *to, const void *from, | 7 | unsigned long raw_copy_from_user(void *to, const void *from, |
8 | unsigned long n) | 8 | unsigned long n) |
9 | { | 9 | { |
10 | if (access_ok(VERIFY_READ, from, n)) | 10 | if (access_ok(from, n)) |
11 | __copy_user_zeroing(to, from, n); | 11 | __copy_user_zeroing(to, from, n); |
12 | else | 12 | else |
13 | memset(to, 0, n); | 13 | memset(to, 0, n); |
@@ -18,7 +18,7 @@ EXPORT_SYMBOL(raw_copy_from_user); | |||
18 | unsigned long raw_copy_to_user(void *to, const void *from, | 18 | unsigned long raw_copy_to_user(void *to, const void *from, |
19 | unsigned long n) | 19 | unsigned long n) |
20 | { | 20 | { |
21 | if (access_ok(VERIFY_WRITE, to, n)) | 21 | if (access_ok(to, n)) |
22 | __copy_user(to, from, n); | 22 | __copy_user(to, from, n); |
23 | return n; | 23 | return n; |
24 | } | 24 | } |
@@ -113,7 +113,7 @@ long strncpy_from_user(char *dst, const char *src, long count) | |||
113 | { | 113 | { |
114 | long res = -EFAULT; | 114 | long res = -EFAULT; |
115 | 115 | ||
116 | if (access_ok(VERIFY_READ, src, 1)) | 116 | if (access_ok(src, 1)) |
117 | __do_strncpy_from_user(dst, src, count, res); | 117 | __do_strncpy_from_user(dst, src, count, res); |
118 | return res; | 118 | return res; |
119 | } | 119 | } |
@@ -236,7 +236,7 @@ do { \ | |||
236 | unsigned long | 236 | unsigned long |
237 | clear_user(void __user *to, unsigned long n) | 237 | clear_user(void __user *to, unsigned long n) |
238 | { | 238 | { |
239 | if (access_ok(VERIFY_WRITE, to, n)) | 239 | if (access_ok(to, n)) |
240 | __do_clear_user(to, n); | 240 | __do_clear_user(to, n); |
241 | return n; | 241 | return n; |
242 | } | 242 | } |
diff --git a/arch/h8300/kernel/signal.c b/arch/h8300/kernel/signal.c index 1e8070d08770..e0f2b708e5d9 100644 --- a/arch/h8300/kernel/signal.c +++ b/arch/h8300/kernel/signal.c | |||
@@ -110,7 +110,7 @@ asmlinkage int sys_rt_sigreturn(void) | |||
110 | sigset_t set; | 110 | sigset_t set; |
111 | int er0; | 111 | int er0; |
112 | 112 | ||
113 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 113 | if (!access_ok(frame, sizeof(*frame))) |
114 | goto badframe; | 114 | goto badframe; |
115 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) | 115 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) |
116 | goto badframe; | 116 | goto badframe; |
@@ -165,7 +165,7 @@ static int setup_rt_frame(struct ksignal *ksig, sigset_t *set, | |||
165 | 165 | ||
166 | frame = get_sigframe(ksig, regs, sizeof(*frame)); | 166 | frame = get_sigframe(ksig, regs, sizeof(*frame)); |
167 | 167 | ||
168 | if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame))) | 168 | if (!access_ok(frame, sizeof(*frame))) |
169 | return -EFAULT; | 169 | return -EFAULT; |
170 | 170 | ||
171 | if (ksig->ka.sa.sa_flags & SA_SIGINFO) | 171 | if (ksig->ka.sa.sa_flags & SA_SIGINFO) |
diff --git a/arch/hexagon/include/asm/futex.h b/arch/hexagon/include/asm/futex.h index c889f5993ecd..cb635216a732 100644 --- a/arch/hexagon/include/asm/futex.h +++ b/arch/hexagon/include/asm/futex.h | |||
@@ -77,7 +77,7 @@ futex_atomic_cmpxchg_inatomic(u32 *uval, u32 __user *uaddr, u32 oldval, | |||
77 | int prev; | 77 | int prev; |
78 | int ret; | 78 | int ret; |
79 | 79 | ||
80 | if (!access_ok(VERIFY_WRITE, uaddr, sizeof(u32))) | 80 | if (!access_ok(uaddr, sizeof(u32))) |
81 | return -EFAULT; | 81 | return -EFAULT; |
82 | 82 | ||
83 | __asm__ __volatile__ ( | 83 | __asm__ __volatile__ ( |
diff --git a/arch/hexagon/include/asm/uaccess.h b/arch/hexagon/include/asm/uaccess.h index 458b69886b34..a30e58d5f351 100644 --- a/arch/hexagon/include/asm/uaccess.h +++ b/arch/hexagon/include/asm/uaccess.h | |||
@@ -29,9 +29,6 @@ | |||
29 | 29 | ||
30 | /* | 30 | /* |
31 | * access_ok: - Checks if a user space pointer is valid | 31 | * access_ok: - Checks if a user space pointer is valid |
32 | * @type: Type of access: %VERIFY_READ or %VERIFY_WRITE. Note that | ||
33 | * %VERIFY_WRITE is a superset of %VERIFY_READ - if it is safe | ||
34 | * to write to a block, it is always safe to read from it. | ||
35 | * @addr: User space pointer to start of block to check | 32 | * @addr: User space pointer to start of block to check |
36 | * @size: Size of block to check | 33 | * @size: Size of block to check |
37 | * | 34 | * |
diff --git a/arch/hexagon/kernel/signal.c b/arch/hexagon/kernel/signal.c index 78aa7304a5c9..31e2cf95f189 100644 --- a/arch/hexagon/kernel/signal.c +++ b/arch/hexagon/kernel/signal.c | |||
@@ -115,7 +115,7 @@ static int setup_rt_frame(struct ksignal *ksig, sigset_t *set, | |||
115 | 115 | ||
116 | frame = get_sigframe(ksig, regs, sizeof(struct rt_sigframe)); | 116 | frame = get_sigframe(ksig, regs, sizeof(struct rt_sigframe)); |
117 | 117 | ||
118 | if (!access_ok(VERIFY_WRITE, frame, sizeof(struct rt_sigframe))) | 118 | if (!access_ok(frame, sizeof(struct rt_sigframe))) |
119 | return -EFAULT; | 119 | return -EFAULT; |
120 | 120 | ||
121 | if (copy_siginfo_to_user(&frame->info, &ksig->info)) | 121 | if (copy_siginfo_to_user(&frame->info, &ksig->info)) |
@@ -244,7 +244,7 @@ asmlinkage int sys_rt_sigreturn(void) | |||
244 | current->restart_block.fn = do_no_restart_syscall; | 244 | current->restart_block.fn = do_no_restart_syscall; |
245 | 245 | ||
246 | frame = (struct rt_sigframe __user *)pt_psp(regs); | 246 | frame = (struct rt_sigframe __user *)pt_psp(regs); |
247 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 247 | if (!access_ok(frame, sizeof(*frame))) |
248 | goto badframe; | 248 | goto badframe; |
249 | if (__copy_from_user(&blocked, &frame->uc.uc_sigmask, sizeof(blocked))) | 249 | if (__copy_from_user(&blocked, &frame->uc.uc_sigmask, sizeof(blocked))) |
250 | goto badframe; | 250 | goto badframe; |
diff --git a/arch/hexagon/mm/uaccess.c b/arch/hexagon/mm/uaccess.c index c599eb126c9e..6f9c4697552c 100644 --- a/arch/hexagon/mm/uaccess.c +++ b/arch/hexagon/mm/uaccess.c | |||
@@ -51,7 +51,7 @@ __kernel_size_t __clear_user_hexagon(void __user *dest, unsigned long count) | |||
51 | 51 | ||
52 | unsigned long clear_user_hexagon(void __user *dest, unsigned long count) | 52 | unsigned long clear_user_hexagon(void __user *dest, unsigned long count) |
53 | { | 53 | { |
54 | if (!access_ok(VERIFY_WRITE, dest, count)) | 54 | if (!access_ok(dest, count)) |
55 | return count; | 55 | return count; |
56 | else | 56 | else |
57 | return __clear_user_hexagon(dest, count); | 57 | return __clear_user_hexagon(dest, count); |
diff --git a/arch/ia64/Kconfig b/arch/ia64/Kconfig index ccd56f5df8cd..8d7396bd1790 100644 --- a/arch/ia64/Kconfig +++ b/arch/ia64/Kconfig | |||
@@ -31,7 +31,7 @@ config IA64 | |||
31 | select HAVE_MEMBLOCK_NODE_MAP | 31 | select HAVE_MEMBLOCK_NODE_MAP |
32 | select HAVE_VIRT_CPU_ACCOUNTING | 32 | select HAVE_VIRT_CPU_ACCOUNTING |
33 | select ARCH_HAS_DMA_COHERENT_TO_PFN if SWIOTLB | 33 | select ARCH_HAS_DMA_COHERENT_TO_PFN if SWIOTLB |
34 | select ARCH_HAS_SYNC_DMA_FOR_CPU | 34 | select ARCH_HAS_SYNC_DMA_FOR_CPU if SWIOTLB |
35 | select VIRT_TO_BUS | 35 | select VIRT_TO_BUS |
36 | select ARCH_DISCARD_MEMBLOCK | 36 | select ARCH_DISCARD_MEMBLOCK |
37 | select GENERIC_IRQ_PROBE | 37 | select GENERIC_IRQ_PROBE |
diff --git a/arch/ia64/include/asm/futex.h b/arch/ia64/include/asm/futex.h index db2dd85918c2..2e106d462196 100644 --- a/arch/ia64/include/asm/futex.h +++ b/arch/ia64/include/asm/futex.h | |||
@@ -86,7 +86,7 @@ static inline int | |||
86 | futex_atomic_cmpxchg_inatomic(u32 *uval, u32 __user *uaddr, | 86 | futex_atomic_cmpxchg_inatomic(u32 *uval, u32 __user *uaddr, |
87 | u32 oldval, u32 newval) | 87 | u32 oldval, u32 newval) |
88 | { | 88 | { |
89 | if (!access_ok(VERIFY_WRITE, uaddr, sizeof(u32))) | 89 | if (!access_ok(uaddr, sizeof(u32))) |
90 | return -EFAULT; | 90 | return -EFAULT; |
91 | 91 | ||
92 | { | 92 | { |
diff --git a/arch/ia64/include/asm/uaccess.h b/arch/ia64/include/asm/uaccess.h index a74524f2d625..306d469e43da 100644 --- a/arch/ia64/include/asm/uaccess.h +++ b/arch/ia64/include/asm/uaccess.h | |||
@@ -67,7 +67,7 @@ static inline int __access_ok(const void __user *p, unsigned long size) | |||
67 | return likely(addr <= seg) && | 67 | return likely(addr <= seg) && |
68 | (seg == KERNEL_DS.seg || likely(REGION_OFFSET(addr) < RGN_MAP_LIMIT)); | 68 | (seg == KERNEL_DS.seg || likely(REGION_OFFSET(addr) < RGN_MAP_LIMIT)); |
69 | } | 69 | } |
70 | #define access_ok(type, addr, size) __access_ok((addr), (size)) | 70 | #define access_ok(addr, size) __access_ok((addr), (size)) |
71 | 71 | ||
72 | /* | 72 | /* |
73 | * These are the main single-value transfer routines. They automatically | 73 | * These are the main single-value transfer routines. They automatically |
diff --git a/arch/ia64/kernel/ptrace.c b/arch/ia64/kernel/ptrace.c index 427cd565fd61..6d50ede0ed69 100644 --- a/arch/ia64/kernel/ptrace.c +++ b/arch/ia64/kernel/ptrace.c | |||
@@ -836,7 +836,7 @@ ptrace_getregs (struct task_struct *child, struct pt_all_user_regs __user *ppr) | |||
836 | char nat = 0; | 836 | char nat = 0; |
837 | int i; | 837 | int i; |
838 | 838 | ||
839 | if (!access_ok(VERIFY_WRITE, ppr, sizeof(struct pt_all_user_regs))) | 839 | if (!access_ok(ppr, sizeof(struct pt_all_user_regs))) |
840 | return -EIO; | 840 | return -EIO; |
841 | 841 | ||
842 | pt = task_pt_regs(child); | 842 | pt = task_pt_regs(child); |
@@ -981,7 +981,7 @@ ptrace_setregs (struct task_struct *child, struct pt_all_user_regs __user *ppr) | |||
981 | 981 | ||
982 | memset(&fpval, 0, sizeof(fpval)); | 982 | memset(&fpval, 0, sizeof(fpval)); |
983 | 983 | ||
984 | if (!access_ok(VERIFY_READ, ppr, sizeof(struct pt_all_user_regs))) | 984 | if (!access_ok(ppr, sizeof(struct pt_all_user_regs))) |
985 | return -EIO; | 985 | return -EIO; |
986 | 986 | ||
987 | pt = task_pt_regs(child); | 987 | pt = task_pt_regs(child); |
diff --git a/arch/ia64/kernel/signal.c b/arch/ia64/kernel/signal.c index 99099f73b207..6062fd14e34e 100644 --- a/arch/ia64/kernel/signal.c +++ b/arch/ia64/kernel/signal.c | |||
@@ -132,7 +132,7 @@ ia64_rt_sigreturn (struct sigscratch *scr) | |||
132 | */ | 132 | */ |
133 | retval = (long) &ia64_strace_leave_kernel; | 133 | retval = (long) &ia64_strace_leave_kernel; |
134 | 134 | ||
135 | if (!access_ok(VERIFY_READ, sc, sizeof(*sc))) | 135 | if (!access_ok(sc, sizeof(*sc))) |
136 | goto give_sigsegv; | 136 | goto give_sigsegv; |
137 | 137 | ||
138 | if (GET_SIGSET(&set, &sc->sc_mask)) | 138 | if (GET_SIGSET(&set, &sc->sc_mask)) |
@@ -264,7 +264,7 @@ setup_frame(struct ksignal *ksig, sigset_t *set, struct sigscratch *scr) | |||
264 | } | 264 | } |
265 | frame = (void __user *) ((new_sp - sizeof(*frame)) & -STACK_ALIGN); | 265 | frame = (void __user *) ((new_sp - sizeof(*frame)) & -STACK_ALIGN); |
266 | 266 | ||
267 | if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame))) { | 267 | if (!access_ok(frame, sizeof(*frame))) { |
268 | force_sigsegv(ksig->sig, current); | 268 | force_sigsegv(ksig->sig, current); |
269 | return 1; | 269 | return 1; |
270 | } | 270 | } |
diff --git a/arch/ia64/mm/init.c b/arch/ia64/mm/init.c index 055382622f07..29d841525ca1 100644 --- a/arch/ia64/mm/init.c +++ b/arch/ia64/mm/init.c | |||
@@ -67,6 +67,7 @@ __ia64_sync_icache_dcache (pte_t pte) | |||
67 | set_bit(PG_arch_1, &page->flags); /* mark page as clean */ | 67 | set_bit(PG_arch_1, &page->flags); /* mark page as clean */ |
68 | } | 68 | } |
69 | 69 | ||
70 | #ifdef CONFIG_SWIOTLB | ||
70 | /* | 71 | /* |
71 | * Since DMA is i-cache coherent, any (complete) pages that were written via | 72 | * Since DMA is i-cache coherent, any (complete) pages that were written via |
72 | * DMA can be marked as "clean" so that lazy_mmu_prot_update() doesn't have to | 73 | * DMA can be marked as "clean" so that lazy_mmu_prot_update() doesn't have to |
@@ -81,6 +82,7 @@ void arch_sync_dma_for_cpu(struct device *dev, phys_addr_t paddr, | |||
81 | set_bit(PG_arch_1, &pfn_to_page(pfn)->flags); | 82 | set_bit(PG_arch_1, &pfn_to_page(pfn)->flags); |
82 | } while (++pfn <= PHYS_PFN(paddr + size - 1)); | 83 | } while (++pfn <= PHYS_PFN(paddr + size - 1)); |
83 | } | 84 | } |
85 | #endif | ||
84 | 86 | ||
85 | inline void | 87 | inline void |
86 | ia64_set_rbs_bot (void) | 88 | ia64_set_rbs_bot (void) |
diff --git a/arch/m68k/include/asm/uaccess_mm.h b/arch/m68k/include/asm/uaccess_mm.h index c4cb889660aa..7e85de984df1 100644 --- a/arch/m68k/include/asm/uaccess_mm.h +++ b/arch/m68k/include/asm/uaccess_mm.h | |||
@@ -10,7 +10,7 @@ | |||
10 | #include <asm/segment.h> | 10 | #include <asm/segment.h> |
11 | 11 | ||
12 | /* We let the MMU do all checking */ | 12 | /* We let the MMU do all checking */ |
13 | static inline int access_ok(int type, const void __user *addr, | 13 | static inline int access_ok(const void __user *addr, |
14 | unsigned long size) | 14 | unsigned long size) |
15 | { | 15 | { |
16 | return 1; | 16 | return 1; |
diff --git a/arch/m68k/include/asm/uaccess_no.h b/arch/m68k/include/asm/uaccess_no.h index 892efb56beef..0134008bf539 100644 --- a/arch/m68k/include/asm/uaccess_no.h +++ b/arch/m68k/include/asm/uaccess_no.h | |||
@@ -10,7 +10,7 @@ | |||
10 | 10 | ||
11 | #include <asm/segment.h> | 11 | #include <asm/segment.h> |
12 | 12 | ||
13 | #define access_ok(type,addr,size) _access_ok((unsigned long)(addr),(size)) | 13 | #define access_ok(addr,size) _access_ok((unsigned long)(addr),(size)) |
14 | 14 | ||
15 | /* | 15 | /* |
16 | * It is not enough to just have access_ok check for a real RAM address. | 16 | * It is not enough to just have access_ok check for a real RAM address. |
diff --git a/arch/m68k/kernel/signal.c b/arch/m68k/kernel/signal.c index 72850b85ecf8..e2a9421c5797 100644 --- a/arch/m68k/kernel/signal.c +++ b/arch/m68k/kernel/signal.c | |||
@@ -787,7 +787,7 @@ asmlinkage int do_sigreturn(struct pt_regs *regs, struct switch_stack *sw) | |||
787 | struct sigframe __user *frame = (struct sigframe __user *)(usp - 4); | 787 | struct sigframe __user *frame = (struct sigframe __user *)(usp - 4); |
788 | sigset_t set; | 788 | sigset_t set; |
789 | 789 | ||
790 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 790 | if (!access_ok(frame, sizeof(*frame))) |
791 | goto badframe; | 791 | goto badframe; |
792 | if (__get_user(set.sig[0], &frame->sc.sc_mask) || | 792 | if (__get_user(set.sig[0], &frame->sc.sc_mask) || |
793 | (_NSIG_WORDS > 1 && | 793 | (_NSIG_WORDS > 1 && |
@@ -812,7 +812,7 @@ asmlinkage int do_rt_sigreturn(struct pt_regs *regs, struct switch_stack *sw) | |||
812 | struct rt_sigframe __user *frame = (struct rt_sigframe __user *)(usp - 4); | 812 | struct rt_sigframe __user *frame = (struct rt_sigframe __user *)(usp - 4); |
813 | sigset_t set; | 813 | sigset_t set; |
814 | 814 | ||
815 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 815 | if (!access_ok(frame, sizeof(*frame))) |
816 | goto badframe; | 816 | goto badframe; |
817 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) | 817 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) |
818 | goto badframe; | 818 | goto badframe; |
diff --git a/arch/microblaze/include/asm/futex.h b/arch/microblaze/include/asm/futex.h index 2572077b04ea..8c90357e5983 100644 --- a/arch/microblaze/include/asm/futex.h +++ b/arch/microblaze/include/asm/futex.h | |||
@@ -71,7 +71,7 @@ futex_atomic_cmpxchg_inatomic(u32 *uval, u32 __user *uaddr, | |||
71 | int ret = 0, cmp; | 71 | int ret = 0, cmp; |
72 | u32 prev; | 72 | u32 prev; |
73 | 73 | ||
74 | if (!access_ok(VERIFY_WRITE, uaddr, sizeof(u32))) | 74 | if (!access_ok(uaddr, sizeof(u32))) |
75 | return -EFAULT; | 75 | return -EFAULT; |
76 | 76 | ||
77 | __asm__ __volatile__ ("1: lwx %1, %3, r0; \ | 77 | __asm__ __volatile__ ("1: lwx %1, %3, r0; \ |
diff --git a/arch/microblaze/include/asm/uaccess.h b/arch/microblaze/include/asm/uaccess.h index 81f16aadbf9e..dbfea093a7c7 100644 --- a/arch/microblaze/include/asm/uaccess.h +++ b/arch/microblaze/include/asm/uaccess.h | |||
@@ -60,26 +60,25 @@ static inline int ___range_ok(unsigned long addr, unsigned long size) | |||
60 | #define __range_ok(addr, size) \ | 60 | #define __range_ok(addr, size) \ |
61 | ___range_ok((unsigned long)(addr), (unsigned long)(size)) | 61 | ___range_ok((unsigned long)(addr), (unsigned long)(size)) |
62 | 62 | ||
63 | #define access_ok(type, addr, size) (__range_ok((addr), (size)) == 0) | 63 | #define access_ok(addr, size) (__range_ok((addr), (size)) == 0) |
64 | 64 | ||
65 | #else | 65 | #else |
66 | 66 | ||
67 | static inline int access_ok(int type, const void __user *addr, | 67 | static inline int access_ok(const void __user *addr, unsigned long size) |
68 | unsigned long size) | ||
69 | { | 68 | { |
70 | if (!size) | 69 | if (!size) |
71 | goto ok; | 70 | goto ok; |
72 | 71 | ||
73 | if ((get_fs().seg < ((unsigned long)addr)) || | 72 | if ((get_fs().seg < ((unsigned long)addr)) || |
74 | (get_fs().seg < ((unsigned long)addr + size - 1))) { | 73 | (get_fs().seg < ((unsigned long)addr + size - 1))) { |
75 | pr_devel("ACCESS fail: %s at 0x%08x (size 0x%x), seg 0x%08x\n", | 74 | pr_devel("ACCESS fail at 0x%08x (size 0x%x), seg 0x%08x\n", |
76 | type ? "WRITE" : "READ ", (__force u32)addr, (u32)size, | 75 | (__force u32)addr, (u32)size, |
77 | (u32)get_fs().seg); | 76 | (u32)get_fs().seg); |
78 | return 0; | 77 | return 0; |
79 | } | 78 | } |
80 | ok: | 79 | ok: |
81 | pr_devel("ACCESS OK: %s at 0x%08x (size 0x%x), seg 0x%08x\n", | 80 | pr_devel("ACCESS OK at 0x%08x (size 0x%x), seg 0x%08x\n", |
82 | type ? "WRITE" : "READ ", (__force u32)addr, (u32)size, | 81 | (__force u32)addr, (u32)size, |
83 | (u32)get_fs().seg); | 82 | (u32)get_fs().seg); |
84 | return 1; | 83 | return 1; |
85 | } | 84 | } |
@@ -120,7 +119,7 @@ static inline unsigned long __must_check clear_user(void __user *to, | |||
120 | unsigned long n) | 119 | unsigned long n) |
121 | { | 120 | { |
122 | might_fault(); | 121 | might_fault(); |
123 | if (unlikely(!access_ok(VERIFY_WRITE, to, n))) | 122 | if (unlikely(!access_ok(to, n))) |
124 | return n; | 123 | return n; |
125 | 124 | ||
126 | return __clear_user(to, n); | 125 | return __clear_user(to, n); |
@@ -174,7 +173,7 @@ extern long __user_bad(void); | |||
174 | const typeof(*(ptr)) __user *__gu_addr = (ptr); \ | 173 | const typeof(*(ptr)) __user *__gu_addr = (ptr); \ |
175 | int __gu_err = 0; \ | 174 | int __gu_err = 0; \ |
176 | \ | 175 | \ |
177 | if (access_ok(VERIFY_READ, __gu_addr, size)) { \ | 176 | if (access_ok(__gu_addr, size)) { \ |
178 | switch (size) { \ | 177 | switch (size) { \ |
179 | case 1: \ | 178 | case 1: \ |
180 | __get_user_asm("lbu", __gu_addr, __gu_val, \ | 179 | __get_user_asm("lbu", __gu_addr, __gu_val, \ |
@@ -286,7 +285,7 @@ extern long __user_bad(void); | |||
286 | typeof(*(ptr)) __user *__pu_addr = (ptr); \ | 285 | typeof(*(ptr)) __user *__pu_addr = (ptr); \ |
287 | int __pu_err = 0; \ | 286 | int __pu_err = 0; \ |
288 | \ | 287 | \ |
289 | if (access_ok(VERIFY_WRITE, __pu_addr, size)) { \ | 288 | if (access_ok(__pu_addr, size)) { \ |
290 | switch (size) { \ | 289 | switch (size) { \ |
291 | case 1: \ | 290 | case 1: \ |
292 | __put_user_asm("sb", __pu_addr, __pu_val, \ | 291 | __put_user_asm("sb", __pu_addr, __pu_val, \ |
@@ -358,7 +357,7 @@ extern int __strncpy_user(char *to, const char __user *from, int len); | |||
358 | static inline long | 357 | static inline long |
359 | strncpy_from_user(char *dst, const char __user *src, long count) | 358 | strncpy_from_user(char *dst, const char __user *src, long count) |
360 | { | 359 | { |
361 | if (!access_ok(VERIFY_READ, src, 1)) | 360 | if (!access_ok(src, 1)) |
362 | return -EFAULT; | 361 | return -EFAULT; |
363 | return __strncpy_user(dst, src, count); | 362 | return __strncpy_user(dst, src, count); |
364 | } | 363 | } |
@@ -372,7 +371,7 @@ extern int __strnlen_user(const char __user *sstr, int len); | |||
372 | 371 | ||
373 | static inline long strnlen_user(const char __user *src, long n) | 372 | static inline long strnlen_user(const char __user *src, long n) |
374 | { | 373 | { |
375 | if (!access_ok(VERIFY_READ, src, 1)) | 374 | if (!access_ok(src, 1)) |
376 | return 0; | 375 | return 0; |
377 | return __strnlen_user(src, n); | 376 | return __strnlen_user(src, n); |
378 | } | 377 | } |
diff --git a/arch/microblaze/kernel/signal.c b/arch/microblaze/kernel/signal.c index 97001524ca2d..0685696349bb 100644 --- a/arch/microblaze/kernel/signal.c +++ b/arch/microblaze/kernel/signal.c | |||
@@ -91,7 +91,7 @@ asmlinkage long sys_rt_sigreturn(struct pt_regs *regs) | |||
91 | /* Always make any pending restarted system calls return -EINTR */ | 91 | /* Always make any pending restarted system calls return -EINTR */ |
92 | current->restart_block.fn = do_no_restart_syscall; | 92 | current->restart_block.fn = do_no_restart_syscall; |
93 | 93 | ||
94 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 94 | if (!access_ok(frame, sizeof(*frame))) |
95 | goto badframe; | 95 | goto badframe; |
96 | 96 | ||
97 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) | 97 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) |
@@ -166,7 +166,7 @@ static int setup_rt_frame(struct ksignal *ksig, sigset_t *set, | |||
166 | 166 | ||
167 | frame = get_sigframe(ksig, regs, sizeof(*frame)); | 167 | frame = get_sigframe(ksig, regs, sizeof(*frame)); |
168 | 168 | ||
169 | if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame))) | 169 | if (!access_ok(frame, sizeof(*frame))) |
170 | return -EFAULT; | 170 | return -EFAULT; |
171 | 171 | ||
172 | if (ksig->ka.sa.sa_flags & SA_SIGINFO) | 172 | if (ksig->ka.sa.sa_flags & SA_SIGINFO) |
diff --git a/arch/mips/include/asm/checksum.h b/arch/mips/include/asm/checksum.h index e8161e4dfde7..dcebaaf8c862 100644 --- a/arch/mips/include/asm/checksum.h +++ b/arch/mips/include/asm/checksum.h | |||
@@ -63,7 +63,7 @@ static inline | |||
63 | __wsum csum_and_copy_from_user(const void __user *src, void *dst, | 63 | __wsum csum_and_copy_from_user(const void __user *src, void *dst, |
64 | int len, __wsum sum, int *err_ptr) | 64 | int len, __wsum sum, int *err_ptr) |
65 | { | 65 | { |
66 | if (access_ok(VERIFY_READ, src, len)) | 66 | if (access_ok(src, len)) |
67 | return csum_partial_copy_from_user(src, dst, len, sum, | 67 | return csum_partial_copy_from_user(src, dst, len, sum, |
68 | err_ptr); | 68 | err_ptr); |
69 | if (len) | 69 | if (len) |
@@ -81,7 +81,7 @@ __wsum csum_and_copy_to_user(const void *src, void __user *dst, int len, | |||
81 | __wsum sum, int *err_ptr) | 81 | __wsum sum, int *err_ptr) |
82 | { | 82 | { |
83 | might_fault(); | 83 | might_fault(); |
84 | if (access_ok(VERIFY_WRITE, dst, len)) { | 84 | if (access_ok(dst, len)) { |
85 | if (uaccess_kernel()) | 85 | if (uaccess_kernel()) |
86 | return __csum_partial_copy_kernel(src, | 86 | return __csum_partial_copy_kernel(src, |
87 | (__force void *)dst, | 87 | (__force void *)dst, |
diff --git a/arch/mips/include/asm/futex.h b/arch/mips/include/asm/futex.h index 8eff134b3a43..c14d798f3888 100644 --- a/arch/mips/include/asm/futex.h +++ b/arch/mips/include/asm/futex.h | |||
@@ -129,7 +129,7 @@ futex_atomic_cmpxchg_inatomic(u32 *uval, u32 __user *uaddr, | |||
129 | int ret = 0; | 129 | int ret = 0; |
130 | u32 val; | 130 | u32 val; |
131 | 131 | ||
132 | if (!access_ok(VERIFY_WRITE, uaddr, sizeof(u32))) | 132 | if (!access_ok(uaddr, sizeof(u32))) |
133 | return -EFAULT; | 133 | return -EFAULT; |
134 | 134 | ||
135 | if (cpu_has_llsc && R10000_LLSC_WAR) { | 135 | if (cpu_has_llsc && R10000_LLSC_WAR) { |
diff --git a/arch/mips/include/asm/termios.h b/arch/mips/include/asm/termios.h index ce2d72e34274..bc29eeacc55a 100644 --- a/arch/mips/include/asm/termios.h +++ b/arch/mips/include/asm/termios.h | |||
@@ -32,7 +32,7 @@ static inline int user_termio_to_kernel_termios(struct ktermios *termios, | |||
32 | unsigned short iflag, oflag, cflag, lflag; | 32 | unsigned short iflag, oflag, cflag, lflag; |
33 | unsigned int err; | 33 | unsigned int err; |
34 | 34 | ||
35 | if (!access_ok(VERIFY_READ, termio, sizeof(struct termio))) | 35 | if (!access_ok(termio, sizeof(struct termio))) |
36 | return -EFAULT; | 36 | return -EFAULT; |
37 | 37 | ||
38 | err = __get_user(iflag, &termio->c_iflag); | 38 | err = __get_user(iflag, &termio->c_iflag); |
@@ -61,7 +61,7 @@ static inline int kernel_termios_to_user_termio(struct termio __user *termio, | |||
61 | { | 61 | { |
62 | int err; | 62 | int err; |
63 | 63 | ||
64 | if (!access_ok(VERIFY_WRITE, termio, sizeof(struct termio))) | 64 | if (!access_ok(termio, sizeof(struct termio))) |
65 | return -EFAULT; | 65 | return -EFAULT; |
66 | 66 | ||
67 | err = __put_user(termios->c_iflag, &termio->c_iflag); | 67 | err = __put_user(termios->c_iflag, &termio->c_iflag); |
diff --git a/arch/mips/include/asm/uaccess.h b/arch/mips/include/asm/uaccess.h index 06629011a434..d43c1dc6ef15 100644 --- a/arch/mips/include/asm/uaccess.h +++ b/arch/mips/include/asm/uaccess.h | |||
@@ -109,9 +109,6 @@ static inline bool eva_kernel_access(void) | |||
109 | 109 | ||
110 | /* | 110 | /* |
111 | * access_ok: - Checks if a user space pointer is valid | 111 | * access_ok: - Checks if a user space pointer is valid |
112 | * @type: Type of access: %VERIFY_READ or %VERIFY_WRITE. Note that | ||
113 | * %VERIFY_WRITE is a superset of %VERIFY_READ - if it is safe | ||
114 | * to write to a block, it is always safe to read from it. | ||
115 | * @addr: User space pointer to start of block to check | 112 | * @addr: User space pointer to start of block to check |
116 | * @size: Size of block to check | 113 | * @size: Size of block to check |
117 | * | 114 | * |
@@ -134,7 +131,7 @@ static inline int __access_ok(const void __user *p, unsigned long size) | |||
134 | return (get_fs().seg & (addr | (addr + size) | __ua_size(size))) == 0; | 131 | return (get_fs().seg & (addr | (addr + size) | __ua_size(size))) == 0; |
135 | } | 132 | } |
136 | 133 | ||
137 | #define access_ok(type, addr, size) \ | 134 | #define access_ok(addr, size) \ |
138 | likely(__access_ok((addr), (size))) | 135 | likely(__access_ok((addr), (size))) |
139 | 136 | ||
140 | /* | 137 | /* |
@@ -304,7 +301,7 @@ do { \ | |||
304 | const __typeof__(*(ptr)) __user * __gu_ptr = (ptr); \ | 301 | const __typeof__(*(ptr)) __user * __gu_ptr = (ptr); \ |
305 | \ | 302 | \ |
306 | might_fault(); \ | 303 | might_fault(); \ |
307 | if (likely(access_ok(VERIFY_READ, __gu_ptr, size))) { \ | 304 | if (likely(access_ok( __gu_ptr, size))) { \ |
308 | if (eva_kernel_access()) \ | 305 | if (eva_kernel_access()) \ |
309 | __get_kernel_common((x), size, __gu_ptr); \ | 306 | __get_kernel_common((x), size, __gu_ptr); \ |
310 | else \ | 307 | else \ |
@@ -446,7 +443,7 @@ do { \ | |||
446 | int __pu_err = -EFAULT; \ | 443 | int __pu_err = -EFAULT; \ |
447 | \ | 444 | \ |
448 | might_fault(); \ | 445 | might_fault(); \ |
449 | if (likely(access_ok(VERIFY_WRITE, __pu_addr, size))) { \ | 446 | if (likely(access_ok( __pu_addr, size))) { \ |
450 | if (eva_kernel_access()) \ | 447 | if (eva_kernel_access()) \ |
451 | __put_kernel_common(__pu_addr, size); \ | 448 | __put_kernel_common(__pu_addr, size); \ |
452 | else \ | 449 | else \ |
@@ -691,8 +688,7 @@ __clear_user(void __user *addr, __kernel_size_t size) | |||
691 | ({ \ | 688 | ({ \ |
692 | void __user * __cl_addr = (addr); \ | 689 | void __user * __cl_addr = (addr); \ |
693 | unsigned long __cl_size = (n); \ | 690 | unsigned long __cl_size = (n); \ |
694 | if (__cl_size && access_ok(VERIFY_WRITE, \ | 691 | if (__cl_size && access_ok(__cl_addr, __cl_size)) \ |
695 | __cl_addr, __cl_size)) \ | ||
696 | __cl_size = __clear_user(__cl_addr, __cl_size); \ | 692 | __cl_size = __clear_user(__cl_addr, __cl_size); \ |
697 | __cl_size; \ | 693 | __cl_size; \ |
698 | }) | 694 | }) |
diff --git a/arch/mips/kernel/mips-r2-to-r6-emul.c b/arch/mips/kernel/mips-r2-to-r6-emul.c index cb22a558431e..c50c89a978f1 100644 --- a/arch/mips/kernel/mips-r2-to-r6-emul.c +++ b/arch/mips/kernel/mips-r2-to-r6-emul.c | |||
@@ -1205,7 +1205,7 @@ fpu_emul: | |||
1205 | case lwl_op: | 1205 | case lwl_op: |
1206 | rt = regs->regs[MIPSInst_RT(inst)]; | 1206 | rt = regs->regs[MIPSInst_RT(inst)]; |
1207 | vaddr = regs->regs[MIPSInst_RS(inst)] + MIPSInst_SIMM(inst); | 1207 | vaddr = regs->regs[MIPSInst_RS(inst)] + MIPSInst_SIMM(inst); |
1208 | if (!access_ok(VERIFY_READ, (void __user *)vaddr, 4)) { | 1208 | if (!access_ok((void __user *)vaddr, 4)) { |
1209 | current->thread.cp0_baduaddr = vaddr; | 1209 | current->thread.cp0_baduaddr = vaddr; |
1210 | err = SIGSEGV; | 1210 | err = SIGSEGV; |
1211 | break; | 1211 | break; |
@@ -1278,7 +1278,7 @@ fpu_emul: | |||
1278 | case lwr_op: | 1278 | case lwr_op: |
1279 | rt = regs->regs[MIPSInst_RT(inst)]; | 1279 | rt = regs->regs[MIPSInst_RT(inst)]; |
1280 | vaddr = regs->regs[MIPSInst_RS(inst)] + MIPSInst_SIMM(inst); | 1280 | vaddr = regs->regs[MIPSInst_RS(inst)] + MIPSInst_SIMM(inst); |
1281 | if (!access_ok(VERIFY_READ, (void __user *)vaddr, 4)) { | 1281 | if (!access_ok((void __user *)vaddr, 4)) { |
1282 | current->thread.cp0_baduaddr = vaddr; | 1282 | current->thread.cp0_baduaddr = vaddr; |
1283 | err = SIGSEGV; | 1283 | err = SIGSEGV; |
1284 | break; | 1284 | break; |
@@ -1352,7 +1352,7 @@ fpu_emul: | |||
1352 | case swl_op: | 1352 | case swl_op: |
1353 | rt = regs->regs[MIPSInst_RT(inst)]; | 1353 | rt = regs->regs[MIPSInst_RT(inst)]; |
1354 | vaddr = regs->regs[MIPSInst_RS(inst)] + MIPSInst_SIMM(inst); | 1354 | vaddr = regs->regs[MIPSInst_RS(inst)] + MIPSInst_SIMM(inst); |
1355 | if (!access_ok(VERIFY_WRITE, (void __user *)vaddr, 4)) { | 1355 | if (!access_ok((void __user *)vaddr, 4)) { |
1356 | current->thread.cp0_baduaddr = vaddr; | 1356 | current->thread.cp0_baduaddr = vaddr; |
1357 | err = SIGSEGV; | 1357 | err = SIGSEGV; |
1358 | break; | 1358 | break; |
@@ -1422,7 +1422,7 @@ fpu_emul: | |||
1422 | case swr_op: | 1422 | case swr_op: |
1423 | rt = regs->regs[MIPSInst_RT(inst)]; | 1423 | rt = regs->regs[MIPSInst_RT(inst)]; |
1424 | vaddr = regs->regs[MIPSInst_RS(inst)] + MIPSInst_SIMM(inst); | 1424 | vaddr = regs->regs[MIPSInst_RS(inst)] + MIPSInst_SIMM(inst); |
1425 | if (!access_ok(VERIFY_WRITE, (void __user *)vaddr, 4)) { | 1425 | if (!access_ok((void __user *)vaddr, 4)) { |
1426 | current->thread.cp0_baduaddr = vaddr; | 1426 | current->thread.cp0_baduaddr = vaddr; |
1427 | err = SIGSEGV; | 1427 | err = SIGSEGV; |
1428 | break; | 1428 | break; |
@@ -1497,7 +1497,7 @@ fpu_emul: | |||
1497 | 1497 | ||
1498 | rt = regs->regs[MIPSInst_RT(inst)]; | 1498 | rt = regs->regs[MIPSInst_RT(inst)]; |
1499 | vaddr = regs->regs[MIPSInst_RS(inst)] + MIPSInst_SIMM(inst); | 1499 | vaddr = regs->regs[MIPSInst_RS(inst)] + MIPSInst_SIMM(inst); |
1500 | if (!access_ok(VERIFY_READ, (void __user *)vaddr, 8)) { | 1500 | if (!access_ok((void __user *)vaddr, 8)) { |
1501 | current->thread.cp0_baduaddr = vaddr; | 1501 | current->thread.cp0_baduaddr = vaddr; |
1502 | err = SIGSEGV; | 1502 | err = SIGSEGV; |
1503 | break; | 1503 | break; |
@@ -1616,7 +1616,7 @@ fpu_emul: | |||
1616 | 1616 | ||
1617 | rt = regs->regs[MIPSInst_RT(inst)]; | 1617 | rt = regs->regs[MIPSInst_RT(inst)]; |
1618 | vaddr = regs->regs[MIPSInst_RS(inst)] + MIPSInst_SIMM(inst); | 1618 | vaddr = regs->regs[MIPSInst_RS(inst)] + MIPSInst_SIMM(inst); |
1619 | if (!access_ok(VERIFY_READ, (void __user *)vaddr, 8)) { | 1619 | if (!access_ok((void __user *)vaddr, 8)) { |
1620 | current->thread.cp0_baduaddr = vaddr; | 1620 | current->thread.cp0_baduaddr = vaddr; |
1621 | err = SIGSEGV; | 1621 | err = SIGSEGV; |
1622 | break; | 1622 | break; |
@@ -1735,7 +1735,7 @@ fpu_emul: | |||
1735 | 1735 | ||
1736 | rt = regs->regs[MIPSInst_RT(inst)]; | 1736 | rt = regs->regs[MIPSInst_RT(inst)]; |
1737 | vaddr = regs->regs[MIPSInst_RS(inst)] + MIPSInst_SIMM(inst); | 1737 | vaddr = regs->regs[MIPSInst_RS(inst)] + MIPSInst_SIMM(inst); |
1738 | if (!access_ok(VERIFY_WRITE, (void __user *)vaddr, 8)) { | 1738 | if (!access_ok((void __user *)vaddr, 8)) { |
1739 | current->thread.cp0_baduaddr = vaddr; | 1739 | current->thread.cp0_baduaddr = vaddr; |
1740 | err = SIGSEGV; | 1740 | err = SIGSEGV; |
1741 | break; | 1741 | break; |
@@ -1853,7 +1853,7 @@ fpu_emul: | |||
1853 | 1853 | ||
1854 | rt = regs->regs[MIPSInst_RT(inst)]; | 1854 | rt = regs->regs[MIPSInst_RT(inst)]; |
1855 | vaddr = regs->regs[MIPSInst_RS(inst)] + MIPSInst_SIMM(inst); | 1855 | vaddr = regs->regs[MIPSInst_RS(inst)] + MIPSInst_SIMM(inst); |
1856 | if (!access_ok(VERIFY_WRITE, (void __user *)vaddr, 8)) { | 1856 | if (!access_ok((void __user *)vaddr, 8)) { |
1857 | current->thread.cp0_baduaddr = vaddr; | 1857 | current->thread.cp0_baduaddr = vaddr; |
1858 | err = SIGSEGV; | 1858 | err = SIGSEGV; |
1859 | break; | 1859 | break; |
@@ -1970,7 +1970,7 @@ fpu_emul: | |||
1970 | err = SIGBUS; | 1970 | err = SIGBUS; |
1971 | break; | 1971 | break; |
1972 | } | 1972 | } |
1973 | if (!access_ok(VERIFY_READ, (void __user *)vaddr, 4)) { | 1973 | if (!access_ok((void __user *)vaddr, 4)) { |
1974 | current->thread.cp0_baduaddr = vaddr; | 1974 | current->thread.cp0_baduaddr = vaddr; |
1975 | err = SIGBUS; | 1975 | err = SIGBUS; |
1976 | break; | 1976 | break; |
@@ -2026,7 +2026,7 @@ fpu_emul: | |||
2026 | err = SIGBUS; | 2026 | err = SIGBUS; |
2027 | break; | 2027 | break; |
2028 | } | 2028 | } |
2029 | if (!access_ok(VERIFY_WRITE, (void __user *)vaddr, 4)) { | 2029 | if (!access_ok((void __user *)vaddr, 4)) { |
2030 | current->thread.cp0_baduaddr = vaddr; | 2030 | current->thread.cp0_baduaddr = vaddr; |
2031 | err = SIGBUS; | 2031 | err = SIGBUS; |
2032 | break; | 2032 | break; |
@@ -2089,7 +2089,7 @@ fpu_emul: | |||
2089 | err = SIGBUS; | 2089 | err = SIGBUS; |
2090 | break; | 2090 | break; |
2091 | } | 2091 | } |
2092 | if (!access_ok(VERIFY_READ, (void __user *)vaddr, 8)) { | 2092 | if (!access_ok((void __user *)vaddr, 8)) { |
2093 | current->thread.cp0_baduaddr = vaddr; | 2093 | current->thread.cp0_baduaddr = vaddr; |
2094 | err = SIGBUS; | 2094 | err = SIGBUS; |
2095 | break; | 2095 | break; |
@@ -2150,7 +2150,7 @@ fpu_emul: | |||
2150 | err = SIGBUS; | 2150 | err = SIGBUS; |
2151 | break; | 2151 | break; |
2152 | } | 2152 | } |
2153 | if (!access_ok(VERIFY_WRITE, (void __user *)vaddr, 8)) { | 2153 | if (!access_ok((void __user *)vaddr, 8)) { |
2154 | current->thread.cp0_baduaddr = vaddr; | 2154 | current->thread.cp0_baduaddr = vaddr; |
2155 | err = SIGBUS; | 2155 | err = SIGBUS; |
2156 | break; | 2156 | break; |
diff --git a/arch/mips/kernel/ptrace.c b/arch/mips/kernel/ptrace.c index ea54575255ea..0057c910bc2f 100644 --- a/arch/mips/kernel/ptrace.c +++ b/arch/mips/kernel/ptrace.c | |||
@@ -71,7 +71,7 @@ int ptrace_getregs(struct task_struct *child, struct user_pt_regs __user *data) | |||
71 | struct pt_regs *regs; | 71 | struct pt_regs *regs; |
72 | int i; | 72 | int i; |
73 | 73 | ||
74 | if (!access_ok(VERIFY_WRITE, data, 38 * 8)) | 74 | if (!access_ok(data, 38 * 8)) |
75 | return -EIO; | 75 | return -EIO; |
76 | 76 | ||
77 | regs = task_pt_regs(child); | 77 | regs = task_pt_regs(child); |
@@ -98,7 +98,7 @@ int ptrace_setregs(struct task_struct *child, struct user_pt_regs __user *data) | |||
98 | struct pt_regs *regs; | 98 | struct pt_regs *regs; |
99 | int i; | 99 | int i; |
100 | 100 | ||
101 | if (!access_ok(VERIFY_READ, data, 38 * 8)) | 101 | if (!access_ok(data, 38 * 8)) |
102 | return -EIO; | 102 | return -EIO; |
103 | 103 | ||
104 | regs = task_pt_regs(child); | 104 | regs = task_pt_regs(child); |
@@ -125,7 +125,7 @@ int ptrace_get_watch_regs(struct task_struct *child, | |||
125 | 125 | ||
126 | if (!cpu_has_watch || boot_cpu_data.watch_reg_use_cnt == 0) | 126 | if (!cpu_has_watch || boot_cpu_data.watch_reg_use_cnt == 0) |
127 | return -EIO; | 127 | return -EIO; |
128 | if (!access_ok(VERIFY_WRITE, addr, sizeof(struct pt_watch_regs))) | 128 | if (!access_ok(addr, sizeof(struct pt_watch_regs))) |
129 | return -EIO; | 129 | return -EIO; |
130 | 130 | ||
131 | #ifdef CONFIG_32BIT | 131 | #ifdef CONFIG_32BIT |
@@ -167,7 +167,7 @@ int ptrace_set_watch_regs(struct task_struct *child, | |||
167 | 167 | ||
168 | if (!cpu_has_watch || boot_cpu_data.watch_reg_use_cnt == 0) | 168 | if (!cpu_has_watch || boot_cpu_data.watch_reg_use_cnt == 0) |
169 | return -EIO; | 169 | return -EIO; |
170 | if (!access_ok(VERIFY_READ, addr, sizeof(struct pt_watch_regs))) | 170 | if (!access_ok(addr, sizeof(struct pt_watch_regs))) |
171 | return -EIO; | 171 | return -EIO; |
172 | /* Check the values. */ | 172 | /* Check the values. */ |
173 | for (i = 0; i < boot_cpu_data.watch_reg_use_cnt; i++) { | 173 | for (i = 0; i < boot_cpu_data.watch_reg_use_cnt; i++) { |
@@ -359,7 +359,7 @@ int ptrace_getfpregs(struct task_struct *child, __u32 __user *data) | |||
359 | { | 359 | { |
360 | int i; | 360 | int i; |
361 | 361 | ||
362 | if (!access_ok(VERIFY_WRITE, data, 33 * 8)) | 362 | if (!access_ok(data, 33 * 8)) |
363 | return -EIO; | 363 | return -EIO; |
364 | 364 | ||
365 | if (tsk_used_math(child)) { | 365 | if (tsk_used_math(child)) { |
@@ -385,7 +385,7 @@ int ptrace_setfpregs(struct task_struct *child, __u32 __user *data) | |||
385 | u32 value; | 385 | u32 value; |
386 | int i; | 386 | int i; |
387 | 387 | ||
388 | if (!access_ok(VERIFY_READ, data, 33 * 8)) | 388 | if (!access_ok(data, 33 * 8)) |
389 | return -EIO; | 389 | return -EIO; |
390 | 390 | ||
391 | init_fp_ctx(child); | 391 | init_fp_ctx(child); |
diff --git a/arch/mips/kernel/signal.c b/arch/mips/kernel/signal.c index d3a23758592c..d75337974ee9 100644 --- a/arch/mips/kernel/signal.c +++ b/arch/mips/kernel/signal.c | |||
@@ -590,7 +590,7 @@ SYSCALL_DEFINE3(sigaction, int, sig, const struct sigaction __user *, act, | |||
590 | if (act) { | 590 | if (act) { |
591 | old_sigset_t mask; | 591 | old_sigset_t mask; |
592 | 592 | ||
593 | if (!access_ok(VERIFY_READ, act, sizeof(*act))) | 593 | if (!access_ok(act, sizeof(*act))) |
594 | return -EFAULT; | 594 | return -EFAULT; |
595 | err |= __get_user(new_ka.sa.sa_handler, &act->sa_handler); | 595 | err |= __get_user(new_ka.sa.sa_handler, &act->sa_handler); |
596 | err |= __get_user(new_ka.sa.sa_flags, &act->sa_flags); | 596 | err |= __get_user(new_ka.sa.sa_flags, &act->sa_flags); |
@@ -604,7 +604,7 @@ SYSCALL_DEFINE3(sigaction, int, sig, const struct sigaction __user *, act, | |||
604 | ret = do_sigaction(sig, act ? &new_ka : NULL, oact ? &old_ka : NULL); | 604 | ret = do_sigaction(sig, act ? &new_ka : NULL, oact ? &old_ka : NULL); |
605 | 605 | ||
606 | if (!ret && oact) { | 606 | if (!ret && oact) { |
607 | if (!access_ok(VERIFY_WRITE, oact, sizeof(*oact))) | 607 | if (!access_ok(oact, sizeof(*oact))) |
608 | return -EFAULT; | 608 | return -EFAULT; |
609 | err |= __put_user(old_ka.sa.sa_flags, &oact->sa_flags); | 609 | err |= __put_user(old_ka.sa.sa_flags, &oact->sa_flags); |
610 | err |= __put_user(old_ka.sa.sa_handler, &oact->sa_handler); | 610 | err |= __put_user(old_ka.sa.sa_handler, &oact->sa_handler); |
@@ -630,7 +630,7 @@ asmlinkage void sys_sigreturn(void) | |||
630 | 630 | ||
631 | regs = current_pt_regs(); | 631 | regs = current_pt_regs(); |
632 | frame = (struct sigframe __user *)regs->regs[29]; | 632 | frame = (struct sigframe __user *)regs->regs[29]; |
633 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 633 | if (!access_ok(frame, sizeof(*frame))) |
634 | goto badframe; | 634 | goto badframe; |
635 | if (__copy_from_user(&blocked, &frame->sf_mask, sizeof(blocked))) | 635 | if (__copy_from_user(&blocked, &frame->sf_mask, sizeof(blocked))) |
636 | goto badframe; | 636 | goto badframe; |
@@ -667,7 +667,7 @@ asmlinkage void sys_rt_sigreturn(void) | |||
667 | 667 | ||
668 | regs = current_pt_regs(); | 668 | regs = current_pt_regs(); |
669 | frame = (struct rt_sigframe __user *)regs->regs[29]; | 669 | frame = (struct rt_sigframe __user *)regs->regs[29]; |
670 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 670 | if (!access_ok(frame, sizeof(*frame))) |
671 | goto badframe; | 671 | goto badframe; |
672 | if (__copy_from_user(&set, &frame->rs_uc.uc_sigmask, sizeof(set))) | 672 | if (__copy_from_user(&set, &frame->rs_uc.uc_sigmask, sizeof(set))) |
673 | goto badframe; | 673 | goto badframe; |
@@ -705,7 +705,7 @@ static int setup_frame(void *sig_return, struct ksignal *ksig, | |||
705 | int err = 0; | 705 | int err = 0; |
706 | 706 | ||
707 | frame = get_sigframe(ksig, regs, sizeof(*frame)); | 707 | frame = get_sigframe(ksig, regs, sizeof(*frame)); |
708 | if (!access_ok(VERIFY_WRITE, frame, sizeof (*frame))) | 708 | if (!access_ok(frame, sizeof (*frame))) |
709 | return -EFAULT; | 709 | return -EFAULT; |
710 | 710 | ||
711 | err |= setup_sigcontext(regs, &frame->sf_sc); | 711 | err |= setup_sigcontext(regs, &frame->sf_sc); |
@@ -744,7 +744,7 @@ static int setup_rt_frame(void *sig_return, struct ksignal *ksig, | |||
744 | int err = 0; | 744 | int err = 0; |
745 | 745 | ||
746 | frame = get_sigframe(ksig, regs, sizeof(*frame)); | 746 | frame = get_sigframe(ksig, regs, sizeof(*frame)); |
747 | if (!access_ok(VERIFY_WRITE, frame, sizeof (*frame))) | 747 | if (!access_ok(frame, sizeof (*frame))) |
748 | return -EFAULT; | 748 | return -EFAULT; |
749 | 749 | ||
750 | /* Create siginfo. */ | 750 | /* Create siginfo. */ |
diff --git a/arch/mips/kernel/signal32.c b/arch/mips/kernel/signal32.c index b5d9e1784aff..59b8965433c2 100644 --- a/arch/mips/kernel/signal32.c +++ b/arch/mips/kernel/signal32.c | |||
@@ -46,7 +46,7 @@ SYSCALL_DEFINE3(32_sigaction, long, sig, const struct compat_sigaction __user *, | |||
46 | old_sigset_t mask; | 46 | old_sigset_t mask; |
47 | s32 handler; | 47 | s32 handler; |
48 | 48 | ||
49 | if (!access_ok(VERIFY_READ, act, sizeof(*act))) | 49 | if (!access_ok(act, sizeof(*act))) |
50 | return -EFAULT; | 50 | return -EFAULT; |
51 | err |= __get_user(handler, &act->sa_handler); | 51 | err |= __get_user(handler, &act->sa_handler); |
52 | new_ka.sa.sa_handler = (void __user *)(s64)handler; | 52 | new_ka.sa.sa_handler = (void __user *)(s64)handler; |
@@ -61,7 +61,7 @@ SYSCALL_DEFINE3(32_sigaction, long, sig, const struct compat_sigaction __user *, | |||
61 | ret = do_sigaction(sig, act ? &new_ka : NULL, oact ? &old_ka : NULL); | 61 | ret = do_sigaction(sig, act ? &new_ka : NULL, oact ? &old_ka : NULL); |
62 | 62 | ||
63 | if (!ret && oact) { | 63 | if (!ret && oact) { |
64 | if (!access_ok(VERIFY_WRITE, oact, sizeof(*oact))) | 64 | if (!access_ok(oact, sizeof(*oact))) |
65 | return -EFAULT; | 65 | return -EFAULT; |
66 | err |= __put_user(old_ka.sa.sa_flags, &oact->sa_flags); | 66 | err |= __put_user(old_ka.sa.sa_flags, &oact->sa_flags); |
67 | err |= __put_user((u32)(u64)old_ka.sa.sa_handler, | 67 | err |= __put_user((u32)(u64)old_ka.sa.sa_handler, |
diff --git a/arch/mips/kernel/signal_n32.c b/arch/mips/kernel/signal_n32.c index 8f65aaf9206d..c498b027823e 100644 --- a/arch/mips/kernel/signal_n32.c +++ b/arch/mips/kernel/signal_n32.c | |||
@@ -73,7 +73,7 @@ asmlinkage void sysn32_rt_sigreturn(void) | |||
73 | 73 | ||
74 | regs = current_pt_regs(); | 74 | regs = current_pt_regs(); |
75 | frame = (struct rt_sigframe_n32 __user *)regs->regs[29]; | 75 | frame = (struct rt_sigframe_n32 __user *)regs->regs[29]; |
76 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 76 | if (!access_ok(frame, sizeof(*frame))) |
77 | goto badframe; | 77 | goto badframe; |
78 | if (__copy_conv_sigset_from_user(&set, &frame->rs_uc.uc_sigmask)) | 78 | if (__copy_conv_sigset_from_user(&set, &frame->rs_uc.uc_sigmask)) |
79 | goto badframe; | 79 | goto badframe; |
@@ -110,7 +110,7 @@ static int setup_rt_frame_n32(void *sig_return, struct ksignal *ksig, | |||
110 | int err = 0; | 110 | int err = 0; |
111 | 111 | ||
112 | frame = get_sigframe(ksig, regs, sizeof(*frame)); | 112 | frame = get_sigframe(ksig, regs, sizeof(*frame)); |
113 | if (!access_ok(VERIFY_WRITE, frame, sizeof (*frame))) | 113 | if (!access_ok(frame, sizeof (*frame))) |
114 | return -EFAULT; | 114 | return -EFAULT; |
115 | 115 | ||
116 | /* Create siginfo. */ | 116 | /* Create siginfo. */ |
diff --git a/arch/mips/kernel/signal_o32.c b/arch/mips/kernel/signal_o32.c index b6e3ddef48a0..df259618e834 100644 --- a/arch/mips/kernel/signal_o32.c +++ b/arch/mips/kernel/signal_o32.c | |||
@@ -118,7 +118,7 @@ static int setup_frame_32(void *sig_return, struct ksignal *ksig, | |||
118 | int err = 0; | 118 | int err = 0; |
119 | 119 | ||
120 | frame = get_sigframe(ksig, regs, sizeof(*frame)); | 120 | frame = get_sigframe(ksig, regs, sizeof(*frame)); |
121 | if (!access_ok(VERIFY_WRITE, frame, sizeof (*frame))) | 121 | if (!access_ok(frame, sizeof (*frame))) |
122 | return -EFAULT; | 122 | return -EFAULT; |
123 | 123 | ||
124 | err |= setup_sigcontext32(regs, &frame->sf_sc); | 124 | err |= setup_sigcontext32(regs, &frame->sf_sc); |
@@ -160,7 +160,7 @@ asmlinkage void sys32_rt_sigreturn(void) | |||
160 | 160 | ||
161 | regs = current_pt_regs(); | 161 | regs = current_pt_regs(); |
162 | frame = (struct rt_sigframe32 __user *)regs->regs[29]; | 162 | frame = (struct rt_sigframe32 __user *)regs->regs[29]; |
163 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 163 | if (!access_ok(frame, sizeof(*frame))) |
164 | goto badframe; | 164 | goto badframe; |
165 | if (__copy_conv_sigset_from_user(&set, &frame->rs_uc.uc_sigmask)) | 165 | if (__copy_conv_sigset_from_user(&set, &frame->rs_uc.uc_sigmask)) |
166 | goto badframe; | 166 | goto badframe; |
@@ -197,7 +197,7 @@ static int setup_rt_frame_32(void *sig_return, struct ksignal *ksig, | |||
197 | int err = 0; | 197 | int err = 0; |
198 | 198 | ||
199 | frame = get_sigframe(ksig, regs, sizeof(*frame)); | 199 | frame = get_sigframe(ksig, regs, sizeof(*frame)); |
200 | if (!access_ok(VERIFY_WRITE, frame, sizeof (*frame))) | 200 | if (!access_ok(frame, sizeof (*frame))) |
201 | return -EFAULT; | 201 | return -EFAULT; |
202 | 202 | ||
203 | /* Convert (siginfo_t -> compat_siginfo_t) and copy to user. */ | 203 | /* Convert (siginfo_t -> compat_siginfo_t) and copy to user. */ |
@@ -262,7 +262,7 @@ asmlinkage void sys32_sigreturn(void) | |||
262 | 262 | ||
263 | regs = current_pt_regs(); | 263 | regs = current_pt_regs(); |
264 | frame = (struct sigframe32 __user *)regs->regs[29]; | 264 | frame = (struct sigframe32 __user *)regs->regs[29]; |
265 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 265 | if (!access_ok(frame, sizeof(*frame))) |
266 | goto badframe; | 266 | goto badframe; |
267 | if (__copy_conv_sigset_from_user(&blocked, &frame->sf_mask)) | 267 | if (__copy_conv_sigset_from_user(&blocked, &frame->sf_mask)) |
268 | goto badframe; | 268 | goto badframe; |
diff --git a/arch/mips/kernel/syscall.c b/arch/mips/kernel/syscall.c index 41a0db08cd37..b6dc78ad5d8c 100644 --- a/arch/mips/kernel/syscall.c +++ b/arch/mips/kernel/syscall.c | |||
@@ -101,7 +101,7 @@ static inline int mips_atomic_set(unsigned long addr, unsigned long new) | |||
101 | if (unlikely(addr & 3)) | 101 | if (unlikely(addr & 3)) |
102 | return -EINVAL; | 102 | return -EINVAL; |
103 | 103 | ||
104 | if (unlikely(!access_ok(VERIFY_WRITE, (const void __user *)addr, 4))) | 104 | if (unlikely(!access_ok((const void __user *)addr, 4))) |
105 | return -EINVAL; | 105 | return -EINVAL; |
106 | 106 | ||
107 | if (cpu_has_llsc && R10000_LLSC_WAR) { | 107 | if (cpu_has_llsc && R10000_LLSC_WAR) { |
diff --git a/arch/mips/kernel/unaligned.c b/arch/mips/kernel/unaligned.c index c60e7719ef77..595ca9c85111 100644 --- a/arch/mips/kernel/unaligned.c +++ b/arch/mips/kernel/unaligned.c | |||
@@ -936,7 +936,7 @@ static void emulate_load_store_insn(struct pt_regs *regs, | |||
936 | if (insn.dsp_format.func == lx_op) { | 936 | if (insn.dsp_format.func == lx_op) { |
937 | switch (insn.dsp_format.op) { | 937 | switch (insn.dsp_format.op) { |
938 | case lwx_op: | 938 | case lwx_op: |
939 | if (!access_ok(VERIFY_READ, addr, 4)) | 939 | if (!access_ok(addr, 4)) |
940 | goto sigbus; | 940 | goto sigbus; |
941 | LoadW(addr, value, res); | 941 | LoadW(addr, value, res); |
942 | if (res) | 942 | if (res) |
@@ -945,7 +945,7 @@ static void emulate_load_store_insn(struct pt_regs *regs, | |||
945 | regs->regs[insn.dsp_format.rd] = value; | 945 | regs->regs[insn.dsp_format.rd] = value; |
946 | break; | 946 | break; |
947 | case lhx_op: | 947 | case lhx_op: |
948 | if (!access_ok(VERIFY_READ, addr, 2)) | 948 | if (!access_ok(addr, 2)) |
949 | goto sigbus; | 949 | goto sigbus; |
950 | LoadHW(addr, value, res); | 950 | LoadHW(addr, value, res); |
951 | if (res) | 951 | if (res) |
@@ -968,7 +968,7 @@ static void emulate_load_store_insn(struct pt_regs *regs, | |||
968 | set_fs(USER_DS); | 968 | set_fs(USER_DS); |
969 | switch (insn.spec3_format.func) { | 969 | switch (insn.spec3_format.func) { |
970 | case lhe_op: | 970 | case lhe_op: |
971 | if (!access_ok(VERIFY_READ, addr, 2)) { | 971 | if (!access_ok(addr, 2)) { |
972 | set_fs(seg); | 972 | set_fs(seg); |
973 | goto sigbus; | 973 | goto sigbus; |
974 | } | 974 | } |
@@ -981,7 +981,7 @@ static void emulate_load_store_insn(struct pt_regs *regs, | |||
981 | regs->regs[insn.spec3_format.rt] = value; | 981 | regs->regs[insn.spec3_format.rt] = value; |
982 | break; | 982 | break; |
983 | case lwe_op: | 983 | case lwe_op: |
984 | if (!access_ok(VERIFY_READ, addr, 4)) { | 984 | if (!access_ok(addr, 4)) { |
985 | set_fs(seg); | 985 | set_fs(seg); |
986 | goto sigbus; | 986 | goto sigbus; |
987 | } | 987 | } |
@@ -994,7 +994,7 @@ static void emulate_load_store_insn(struct pt_regs *regs, | |||
994 | regs->regs[insn.spec3_format.rt] = value; | 994 | regs->regs[insn.spec3_format.rt] = value; |
995 | break; | 995 | break; |
996 | case lhue_op: | 996 | case lhue_op: |
997 | if (!access_ok(VERIFY_READ, addr, 2)) { | 997 | if (!access_ok(addr, 2)) { |
998 | set_fs(seg); | 998 | set_fs(seg); |
999 | goto sigbus; | 999 | goto sigbus; |
1000 | } | 1000 | } |
@@ -1007,7 +1007,7 @@ static void emulate_load_store_insn(struct pt_regs *regs, | |||
1007 | regs->regs[insn.spec3_format.rt] = value; | 1007 | regs->regs[insn.spec3_format.rt] = value; |
1008 | break; | 1008 | break; |
1009 | case she_op: | 1009 | case she_op: |
1010 | if (!access_ok(VERIFY_WRITE, addr, 2)) { | 1010 | if (!access_ok(addr, 2)) { |
1011 | set_fs(seg); | 1011 | set_fs(seg); |
1012 | goto sigbus; | 1012 | goto sigbus; |
1013 | } | 1013 | } |
@@ -1020,7 +1020,7 @@ static void emulate_load_store_insn(struct pt_regs *regs, | |||
1020 | } | 1020 | } |
1021 | break; | 1021 | break; |
1022 | case swe_op: | 1022 | case swe_op: |
1023 | if (!access_ok(VERIFY_WRITE, addr, 4)) { | 1023 | if (!access_ok(addr, 4)) { |
1024 | set_fs(seg); | 1024 | set_fs(seg); |
1025 | goto sigbus; | 1025 | goto sigbus; |
1026 | } | 1026 | } |
@@ -1041,7 +1041,7 @@ static void emulate_load_store_insn(struct pt_regs *regs, | |||
1041 | #endif | 1041 | #endif |
1042 | break; | 1042 | break; |
1043 | case lh_op: | 1043 | case lh_op: |
1044 | if (!access_ok(VERIFY_READ, addr, 2)) | 1044 | if (!access_ok(addr, 2)) |
1045 | goto sigbus; | 1045 | goto sigbus; |
1046 | 1046 | ||
1047 | if (IS_ENABLED(CONFIG_EVA)) { | 1047 | if (IS_ENABLED(CONFIG_EVA)) { |
@@ -1060,7 +1060,7 @@ static void emulate_load_store_insn(struct pt_regs *regs, | |||
1060 | break; | 1060 | break; |
1061 | 1061 | ||
1062 | case lw_op: | 1062 | case lw_op: |
1063 | if (!access_ok(VERIFY_READ, addr, 4)) | 1063 | if (!access_ok(addr, 4)) |
1064 | goto sigbus; | 1064 | goto sigbus; |
1065 | 1065 | ||
1066 | if (IS_ENABLED(CONFIG_EVA)) { | 1066 | if (IS_ENABLED(CONFIG_EVA)) { |
@@ -1079,7 +1079,7 @@ static void emulate_load_store_insn(struct pt_regs *regs, | |||
1079 | break; | 1079 | break; |
1080 | 1080 | ||
1081 | case lhu_op: | 1081 | case lhu_op: |
1082 | if (!access_ok(VERIFY_READ, addr, 2)) | 1082 | if (!access_ok(addr, 2)) |
1083 | goto sigbus; | 1083 | goto sigbus; |
1084 | 1084 | ||
1085 | if (IS_ENABLED(CONFIG_EVA)) { | 1085 | if (IS_ENABLED(CONFIG_EVA)) { |
@@ -1106,7 +1106,7 @@ static void emulate_load_store_insn(struct pt_regs *regs, | |||
1106 | * would blow up, so for now we don't handle unaligned 64-bit | 1106 | * would blow up, so for now we don't handle unaligned 64-bit |
1107 | * instructions on 32-bit kernels. | 1107 | * instructions on 32-bit kernels. |
1108 | */ | 1108 | */ |
1109 | if (!access_ok(VERIFY_READ, addr, 4)) | 1109 | if (!access_ok(addr, 4)) |
1110 | goto sigbus; | 1110 | goto sigbus; |
1111 | 1111 | ||
1112 | LoadWU(addr, value, res); | 1112 | LoadWU(addr, value, res); |
@@ -1129,7 +1129,7 @@ static void emulate_load_store_insn(struct pt_regs *regs, | |||
1129 | * would blow up, so for now we don't handle unaligned 64-bit | 1129 | * would blow up, so for now we don't handle unaligned 64-bit |
1130 | * instructions on 32-bit kernels. | 1130 | * instructions on 32-bit kernels. |
1131 | */ | 1131 | */ |
1132 | if (!access_ok(VERIFY_READ, addr, 8)) | 1132 | if (!access_ok(addr, 8)) |
1133 | goto sigbus; | 1133 | goto sigbus; |
1134 | 1134 | ||
1135 | LoadDW(addr, value, res); | 1135 | LoadDW(addr, value, res); |
@@ -1144,7 +1144,7 @@ static void emulate_load_store_insn(struct pt_regs *regs, | |||
1144 | goto sigill; | 1144 | goto sigill; |
1145 | 1145 | ||
1146 | case sh_op: | 1146 | case sh_op: |
1147 | if (!access_ok(VERIFY_WRITE, addr, 2)) | 1147 | if (!access_ok(addr, 2)) |
1148 | goto sigbus; | 1148 | goto sigbus; |
1149 | 1149 | ||
1150 | compute_return_epc(regs); | 1150 | compute_return_epc(regs); |
@@ -1164,7 +1164,7 @@ static void emulate_load_store_insn(struct pt_regs *regs, | |||
1164 | break; | 1164 | break; |
1165 | 1165 | ||
1166 | case sw_op: | 1166 | case sw_op: |
1167 | if (!access_ok(VERIFY_WRITE, addr, 4)) | 1167 | if (!access_ok(addr, 4)) |
1168 | goto sigbus; | 1168 | goto sigbus; |
1169 | 1169 | ||
1170 | compute_return_epc(regs); | 1170 | compute_return_epc(regs); |
@@ -1192,7 +1192,7 @@ static void emulate_load_store_insn(struct pt_regs *regs, | |||
1192 | * would blow up, so for now we don't handle unaligned 64-bit | 1192 | * would blow up, so for now we don't handle unaligned 64-bit |
1193 | * instructions on 32-bit kernels. | 1193 | * instructions on 32-bit kernels. |
1194 | */ | 1194 | */ |
1195 | if (!access_ok(VERIFY_WRITE, addr, 8)) | 1195 | if (!access_ok(addr, 8)) |
1196 | goto sigbus; | 1196 | goto sigbus; |
1197 | 1197 | ||
1198 | compute_return_epc(regs); | 1198 | compute_return_epc(regs); |
@@ -1254,7 +1254,7 @@ static void emulate_load_store_insn(struct pt_regs *regs, | |||
1254 | 1254 | ||
1255 | switch (insn.msa_mi10_format.func) { | 1255 | switch (insn.msa_mi10_format.func) { |
1256 | case msa_ld_op: | 1256 | case msa_ld_op: |
1257 | if (!access_ok(VERIFY_READ, addr, sizeof(*fpr))) | 1257 | if (!access_ok(addr, sizeof(*fpr))) |
1258 | goto sigbus; | 1258 | goto sigbus; |
1259 | 1259 | ||
1260 | do { | 1260 | do { |
@@ -1290,7 +1290,7 @@ static void emulate_load_store_insn(struct pt_regs *regs, | |||
1290 | break; | 1290 | break; |
1291 | 1291 | ||
1292 | case msa_st_op: | 1292 | case msa_st_op: |
1293 | if (!access_ok(VERIFY_WRITE, addr, sizeof(*fpr))) | 1293 | if (!access_ok(addr, sizeof(*fpr))) |
1294 | goto sigbus; | 1294 | goto sigbus; |
1295 | 1295 | ||
1296 | /* | 1296 | /* |
@@ -1463,7 +1463,7 @@ static void emulate_load_store_microMIPS(struct pt_regs *regs, | |||
1463 | if (reg == 31) | 1463 | if (reg == 31) |
1464 | goto sigbus; | 1464 | goto sigbus; |
1465 | 1465 | ||
1466 | if (!access_ok(VERIFY_READ, addr, 8)) | 1466 | if (!access_ok(addr, 8)) |
1467 | goto sigbus; | 1467 | goto sigbus; |
1468 | 1468 | ||
1469 | LoadW(addr, value, res); | 1469 | LoadW(addr, value, res); |
@@ -1482,7 +1482,7 @@ static void emulate_load_store_microMIPS(struct pt_regs *regs, | |||
1482 | if (reg == 31) | 1482 | if (reg == 31) |
1483 | goto sigbus; | 1483 | goto sigbus; |
1484 | 1484 | ||
1485 | if (!access_ok(VERIFY_WRITE, addr, 8)) | 1485 | if (!access_ok(addr, 8)) |
1486 | goto sigbus; | 1486 | goto sigbus; |
1487 | 1487 | ||
1488 | value = regs->regs[reg]; | 1488 | value = regs->regs[reg]; |
@@ -1502,7 +1502,7 @@ static void emulate_load_store_microMIPS(struct pt_regs *regs, | |||
1502 | if (reg == 31) | 1502 | if (reg == 31) |
1503 | goto sigbus; | 1503 | goto sigbus; |
1504 | 1504 | ||
1505 | if (!access_ok(VERIFY_READ, addr, 16)) | 1505 | if (!access_ok(addr, 16)) |
1506 | goto sigbus; | 1506 | goto sigbus; |
1507 | 1507 | ||
1508 | LoadDW(addr, value, res); | 1508 | LoadDW(addr, value, res); |
@@ -1525,7 +1525,7 @@ static void emulate_load_store_microMIPS(struct pt_regs *regs, | |||
1525 | if (reg == 31) | 1525 | if (reg == 31) |
1526 | goto sigbus; | 1526 | goto sigbus; |
1527 | 1527 | ||
1528 | if (!access_ok(VERIFY_WRITE, addr, 16)) | 1528 | if (!access_ok(addr, 16)) |
1529 | goto sigbus; | 1529 | goto sigbus; |
1530 | 1530 | ||
1531 | value = regs->regs[reg]; | 1531 | value = regs->regs[reg]; |
@@ -1548,11 +1548,10 @@ static void emulate_load_store_microMIPS(struct pt_regs *regs, | |||
1548 | if ((rvar > 9) || !reg) | 1548 | if ((rvar > 9) || !reg) |
1549 | goto sigill; | 1549 | goto sigill; |
1550 | if (reg & 0x10) { | 1550 | if (reg & 0x10) { |
1551 | if (!access_ok | 1551 | if (!access_ok(addr, 4 * (rvar + 1))) |
1552 | (VERIFY_READ, addr, 4 * (rvar + 1))) | ||
1553 | goto sigbus; | 1552 | goto sigbus; |
1554 | } else { | 1553 | } else { |
1555 | if (!access_ok(VERIFY_READ, addr, 4 * rvar)) | 1554 | if (!access_ok(addr, 4 * rvar)) |
1556 | goto sigbus; | 1555 | goto sigbus; |
1557 | } | 1556 | } |
1558 | if (rvar == 9) | 1557 | if (rvar == 9) |
@@ -1585,11 +1584,10 @@ static void emulate_load_store_microMIPS(struct pt_regs *regs, | |||
1585 | if ((rvar > 9) || !reg) | 1584 | if ((rvar > 9) || !reg) |
1586 | goto sigill; | 1585 | goto sigill; |
1587 | if (reg & 0x10) { | 1586 | if (reg & 0x10) { |
1588 | if (!access_ok | 1587 | if (!access_ok(addr, 4 * (rvar + 1))) |
1589 | (VERIFY_WRITE, addr, 4 * (rvar + 1))) | ||
1590 | goto sigbus; | 1588 | goto sigbus; |
1591 | } else { | 1589 | } else { |
1592 | if (!access_ok(VERIFY_WRITE, addr, 4 * rvar)) | 1590 | if (!access_ok(addr, 4 * rvar)) |
1593 | goto sigbus; | 1591 | goto sigbus; |
1594 | } | 1592 | } |
1595 | if (rvar == 9) | 1593 | if (rvar == 9) |
@@ -1623,11 +1621,10 @@ static void emulate_load_store_microMIPS(struct pt_regs *regs, | |||
1623 | if ((rvar > 9) || !reg) | 1621 | if ((rvar > 9) || !reg) |
1624 | goto sigill; | 1622 | goto sigill; |
1625 | if (reg & 0x10) { | 1623 | if (reg & 0x10) { |
1626 | if (!access_ok | 1624 | if (!access_ok(addr, 8 * (rvar + 1))) |
1627 | (VERIFY_READ, addr, 8 * (rvar + 1))) | ||
1628 | goto sigbus; | 1625 | goto sigbus; |
1629 | } else { | 1626 | } else { |
1630 | if (!access_ok(VERIFY_READ, addr, 8 * rvar)) | 1627 | if (!access_ok(addr, 8 * rvar)) |
1631 | goto sigbus; | 1628 | goto sigbus; |
1632 | } | 1629 | } |
1633 | if (rvar == 9) | 1630 | if (rvar == 9) |
@@ -1665,11 +1662,10 @@ static void emulate_load_store_microMIPS(struct pt_regs *regs, | |||
1665 | if ((rvar > 9) || !reg) | 1662 | if ((rvar > 9) || !reg) |
1666 | goto sigill; | 1663 | goto sigill; |
1667 | if (reg & 0x10) { | 1664 | if (reg & 0x10) { |
1668 | if (!access_ok | 1665 | if (!access_ok(addr, 8 * (rvar + 1))) |
1669 | (VERIFY_WRITE, addr, 8 * (rvar + 1))) | ||
1670 | goto sigbus; | 1666 | goto sigbus; |
1671 | } else { | 1667 | } else { |
1672 | if (!access_ok(VERIFY_WRITE, addr, 8 * rvar)) | 1668 | if (!access_ok(addr, 8 * rvar)) |
1673 | goto sigbus; | 1669 | goto sigbus; |
1674 | } | 1670 | } |
1675 | if (rvar == 9) | 1671 | if (rvar == 9) |
@@ -1788,7 +1784,7 @@ fpu_emul: | |||
1788 | case mm_lwm16_op: | 1784 | case mm_lwm16_op: |
1789 | reg = insn.mm16_m_format.rlist; | 1785 | reg = insn.mm16_m_format.rlist; |
1790 | rvar = reg + 1; | 1786 | rvar = reg + 1; |
1791 | if (!access_ok(VERIFY_READ, addr, 4 * rvar)) | 1787 | if (!access_ok(addr, 4 * rvar)) |
1792 | goto sigbus; | 1788 | goto sigbus; |
1793 | 1789 | ||
1794 | for (i = 16; rvar; rvar--, i++) { | 1790 | for (i = 16; rvar; rvar--, i++) { |
@@ -1808,7 +1804,7 @@ fpu_emul: | |||
1808 | case mm_swm16_op: | 1804 | case mm_swm16_op: |
1809 | reg = insn.mm16_m_format.rlist; | 1805 | reg = insn.mm16_m_format.rlist; |
1810 | rvar = reg + 1; | 1806 | rvar = reg + 1; |
1811 | if (!access_ok(VERIFY_WRITE, addr, 4 * rvar)) | 1807 | if (!access_ok(addr, 4 * rvar)) |
1812 | goto sigbus; | 1808 | goto sigbus; |
1813 | 1809 | ||
1814 | for (i = 16; rvar; rvar--, i++) { | 1810 | for (i = 16; rvar; rvar--, i++) { |
@@ -1862,7 +1858,7 @@ fpu_emul: | |||
1862 | } | 1858 | } |
1863 | 1859 | ||
1864 | loadHW: | 1860 | loadHW: |
1865 | if (!access_ok(VERIFY_READ, addr, 2)) | 1861 | if (!access_ok(addr, 2)) |
1866 | goto sigbus; | 1862 | goto sigbus; |
1867 | 1863 | ||
1868 | LoadHW(addr, value, res); | 1864 | LoadHW(addr, value, res); |
@@ -1872,7 +1868,7 @@ loadHW: | |||
1872 | goto success; | 1868 | goto success; |
1873 | 1869 | ||
1874 | loadHWU: | 1870 | loadHWU: |
1875 | if (!access_ok(VERIFY_READ, addr, 2)) | 1871 | if (!access_ok(addr, 2)) |
1876 | goto sigbus; | 1872 | goto sigbus; |
1877 | 1873 | ||
1878 | LoadHWU(addr, value, res); | 1874 | LoadHWU(addr, value, res); |
@@ -1882,7 +1878,7 @@ loadHWU: | |||
1882 | goto success; | 1878 | goto success; |
1883 | 1879 | ||
1884 | loadW: | 1880 | loadW: |
1885 | if (!access_ok(VERIFY_READ, addr, 4)) | 1881 | if (!access_ok(addr, 4)) |
1886 | goto sigbus; | 1882 | goto sigbus; |
1887 | 1883 | ||
1888 | LoadW(addr, value, res); | 1884 | LoadW(addr, value, res); |
@@ -1900,7 +1896,7 @@ loadWU: | |||
1900 | * would blow up, so for now we don't handle unaligned 64-bit | 1896 | * would blow up, so for now we don't handle unaligned 64-bit |
1901 | * instructions on 32-bit kernels. | 1897 | * instructions on 32-bit kernels. |
1902 | */ | 1898 | */ |
1903 | if (!access_ok(VERIFY_READ, addr, 4)) | 1899 | if (!access_ok(addr, 4)) |
1904 | goto sigbus; | 1900 | goto sigbus; |
1905 | 1901 | ||
1906 | LoadWU(addr, value, res); | 1902 | LoadWU(addr, value, res); |
@@ -1922,7 +1918,7 @@ loadDW: | |||
1922 | * would blow up, so for now we don't handle unaligned 64-bit | 1918 | * would blow up, so for now we don't handle unaligned 64-bit |
1923 | * instructions on 32-bit kernels. | 1919 | * instructions on 32-bit kernels. |
1924 | */ | 1920 | */ |
1925 | if (!access_ok(VERIFY_READ, addr, 8)) | 1921 | if (!access_ok(addr, 8)) |
1926 | goto sigbus; | 1922 | goto sigbus; |
1927 | 1923 | ||
1928 | LoadDW(addr, value, res); | 1924 | LoadDW(addr, value, res); |
@@ -1936,7 +1932,7 @@ loadDW: | |||
1936 | goto sigill; | 1932 | goto sigill; |
1937 | 1933 | ||
1938 | storeHW: | 1934 | storeHW: |
1939 | if (!access_ok(VERIFY_WRITE, addr, 2)) | 1935 | if (!access_ok(addr, 2)) |
1940 | goto sigbus; | 1936 | goto sigbus; |
1941 | 1937 | ||
1942 | value = regs->regs[reg]; | 1938 | value = regs->regs[reg]; |
@@ -1946,7 +1942,7 @@ storeHW: | |||
1946 | goto success; | 1942 | goto success; |
1947 | 1943 | ||
1948 | storeW: | 1944 | storeW: |
1949 | if (!access_ok(VERIFY_WRITE, addr, 4)) | 1945 | if (!access_ok(addr, 4)) |
1950 | goto sigbus; | 1946 | goto sigbus; |
1951 | 1947 | ||
1952 | value = regs->regs[reg]; | 1948 | value = regs->regs[reg]; |
@@ -1964,7 +1960,7 @@ storeDW: | |||
1964 | * would blow up, so for now we don't handle unaligned 64-bit | 1960 | * would blow up, so for now we don't handle unaligned 64-bit |
1965 | * instructions on 32-bit kernels. | 1961 | * instructions on 32-bit kernels. |
1966 | */ | 1962 | */ |
1967 | if (!access_ok(VERIFY_WRITE, addr, 8)) | 1963 | if (!access_ok(addr, 8)) |
1968 | goto sigbus; | 1964 | goto sigbus; |
1969 | 1965 | ||
1970 | value = regs->regs[reg]; | 1966 | value = regs->regs[reg]; |
@@ -2122,7 +2118,7 @@ static void emulate_load_store_MIPS16e(struct pt_regs *regs, void __user * addr) | |||
2122 | goto sigbus; | 2118 | goto sigbus; |
2123 | 2119 | ||
2124 | case MIPS16e_lh_op: | 2120 | case MIPS16e_lh_op: |
2125 | if (!access_ok(VERIFY_READ, addr, 2)) | 2121 | if (!access_ok(addr, 2)) |
2126 | goto sigbus; | 2122 | goto sigbus; |
2127 | 2123 | ||
2128 | LoadHW(addr, value, res); | 2124 | LoadHW(addr, value, res); |
@@ -2133,7 +2129,7 @@ static void emulate_load_store_MIPS16e(struct pt_regs *regs, void __user * addr) | |||
2133 | break; | 2129 | break; |
2134 | 2130 | ||
2135 | case MIPS16e_lhu_op: | 2131 | case MIPS16e_lhu_op: |
2136 | if (!access_ok(VERIFY_READ, addr, 2)) | 2132 | if (!access_ok(addr, 2)) |
2137 | goto sigbus; | 2133 | goto sigbus; |
2138 | 2134 | ||
2139 | LoadHWU(addr, value, res); | 2135 | LoadHWU(addr, value, res); |
@@ -2146,7 +2142,7 @@ static void emulate_load_store_MIPS16e(struct pt_regs *regs, void __user * addr) | |||
2146 | case MIPS16e_lw_op: | 2142 | case MIPS16e_lw_op: |
2147 | case MIPS16e_lwpc_op: | 2143 | case MIPS16e_lwpc_op: |
2148 | case MIPS16e_lwsp_op: | 2144 | case MIPS16e_lwsp_op: |
2149 | if (!access_ok(VERIFY_READ, addr, 4)) | 2145 | if (!access_ok(addr, 4)) |
2150 | goto sigbus; | 2146 | goto sigbus; |
2151 | 2147 | ||
2152 | LoadW(addr, value, res); | 2148 | LoadW(addr, value, res); |
@@ -2165,7 +2161,7 @@ static void emulate_load_store_MIPS16e(struct pt_regs *regs, void __user * addr) | |||
2165 | * would blow up, so for now we don't handle unaligned 64-bit | 2161 | * would blow up, so for now we don't handle unaligned 64-bit |
2166 | * instructions on 32-bit kernels. | 2162 | * instructions on 32-bit kernels. |
2167 | */ | 2163 | */ |
2168 | if (!access_ok(VERIFY_READ, addr, 4)) | 2164 | if (!access_ok(addr, 4)) |
2169 | goto sigbus; | 2165 | goto sigbus; |
2170 | 2166 | ||
2171 | LoadWU(addr, value, res); | 2167 | LoadWU(addr, value, res); |
@@ -2189,7 +2185,7 @@ loadDW: | |||
2189 | * would blow up, so for now we don't handle unaligned 64-bit | 2185 | * would blow up, so for now we don't handle unaligned 64-bit |
2190 | * instructions on 32-bit kernels. | 2186 | * instructions on 32-bit kernels. |
2191 | */ | 2187 | */ |
2192 | if (!access_ok(VERIFY_READ, addr, 8)) | 2188 | if (!access_ok(addr, 8)) |
2193 | goto sigbus; | 2189 | goto sigbus; |
2194 | 2190 | ||
2195 | LoadDW(addr, value, res); | 2191 | LoadDW(addr, value, res); |
@@ -2204,7 +2200,7 @@ loadDW: | |||
2204 | goto sigill; | 2200 | goto sigill; |
2205 | 2201 | ||
2206 | case MIPS16e_sh_op: | 2202 | case MIPS16e_sh_op: |
2207 | if (!access_ok(VERIFY_WRITE, addr, 2)) | 2203 | if (!access_ok(addr, 2)) |
2208 | goto sigbus; | 2204 | goto sigbus; |
2209 | 2205 | ||
2210 | MIPS16e_compute_return_epc(regs, &oldinst); | 2206 | MIPS16e_compute_return_epc(regs, &oldinst); |
@@ -2217,7 +2213,7 @@ loadDW: | |||
2217 | case MIPS16e_sw_op: | 2213 | case MIPS16e_sw_op: |
2218 | case MIPS16e_swsp_op: | 2214 | case MIPS16e_swsp_op: |
2219 | case MIPS16e_i8_op: /* actually - MIPS16e_swrasp_func */ | 2215 | case MIPS16e_i8_op: /* actually - MIPS16e_swrasp_func */ |
2220 | if (!access_ok(VERIFY_WRITE, addr, 4)) | 2216 | if (!access_ok(addr, 4)) |
2221 | goto sigbus; | 2217 | goto sigbus; |
2222 | 2218 | ||
2223 | MIPS16e_compute_return_epc(regs, &oldinst); | 2219 | MIPS16e_compute_return_epc(regs, &oldinst); |
@@ -2237,7 +2233,7 @@ writeDW: | |||
2237 | * would blow up, so for now we don't handle unaligned 64-bit | 2233 | * would blow up, so for now we don't handle unaligned 64-bit |
2238 | * instructions on 32-bit kernels. | 2234 | * instructions on 32-bit kernels. |
2239 | */ | 2235 | */ |
2240 | if (!access_ok(VERIFY_WRITE, addr, 8)) | 2236 | if (!access_ok(addr, 8)) |
2241 | goto sigbus; | 2237 | goto sigbus; |
2242 | 2238 | ||
2243 | MIPS16e_compute_return_epc(regs, &oldinst); | 2239 | MIPS16e_compute_return_epc(regs, &oldinst); |
diff --git a/arch/mips/math-emu/cp1emu.c b/arch/mips/math-emu/cp1emu.c index 82e2993c1a2c..e60e29078ef5 100644 --- a/arch/mips/math-emu/cp1emu.c +++ b/arch/mips/math-emu/cp1emu.c | |||
@@ -1063,7 +1063,7 @@ emul: | |||
1063 | MIPSInst_SIMM(ir)); | 1063 | MIPSInst_SIMM(ir)); |
1064 | MIPS_FPU_EMU_INC_STATS(loads); | 1064 | MIPS_FPU_EMU_INC_STATS(loads); |
1065 | 1065 | ||
1066 | if (!access_ok(VERIFY_READ, dva, sizeof(u64))) { | 1066 | if (!access_ok(dva, sizeof(u64))) { |
1067 | MIPS_FPU_EMU_INC_STATS(errors); | 1067 | MIPS_FPU_EMU_INC_STATS(errors); |
1068 | *fault_addr = dva; | 1068 | *fault_addr = dva; |
1069 | return SIGBUS; | 1069 | return SIGBUS; |
@@ -1081,7 +1081,7 @@ emul: | |||
1081 | MIPSInst_SIMM(ir)); | 1081 | MIPSInst_SIMM(ir)); |
1082 | MIPS_FPU_EMU_INC_STATS(stores); | 1082 | MIPS_FPU_EMU_INC_STATS(stores); |
1083 | DIFROMREG(dval, MIPSInst_RT(ir)); | 1083 | DIFROMREG(dval, MIPSInst_RT(ir)); |
1084 | if (!access_ok(VERIFY_WRITE, dva, sizeof(u64))) { | 1084 | if (!access_ok(dva, sizeof(u64))) { |
1085 | MIPS_FPU_EMU_INC_STATS(errors); | 1085 | MIPS_FPU_EMU_INC_STATS(errors); |
1086 | *fault_addr = dva; | 1086 | *fault_addr = dva; |
1087 | return SIGBUS; | 1087 | return SIGBUS; |
@@ -1097,7 +1097,7 @@ emul: | |||
1097 | wva = (u32 __user *) (xcp->regs[MIPSInst_RS(ir)] + | 1097 | wva = (u32 __user *) (xcp->regs[MIPSInst_RS(ir)] + |
1098 | MIPSInst_SIMM(ir)); | 1098 | MIPSInst_SIMM(ir)); |
1099 | MIPS_FPU_EMU_INC_STATS(loads); | 1099 | MIPS_FPU_EMU_INC_STATS(loads); |
1100 | if (!access_ok(VERIFY_READ, wva, sizeof(u32))) { | 1100 | if (!access_ok(wva, sizeof(u32))) { |
1101 | MIPS_FPU_EMU_INC_STATS(errors); | 1101 | MIPS_FPU_EMU_INC_STATS(errors); |
1102 | *fault_addr = wva; | 1102 | *fault_addr = wva; |
1103 | return SIGBUS; | 1103 | return SIGBUS; |
@@ -1115,7 +1115,7 @@ emul: | |||
1115 | MIPSInst_SIMM(ir)); | 1115 | MIPSInst_SIMM(ir)); |
1116 | MIPS_FPU_EMU_INC_STATS(stores); | 1116 | MIPS_FPU_EMU_INC_STATS(stores); |
1117 | SIFROMREG(wval, MIPSInst_RT(ir)); | 1117 | SIFROMREG(wval, MIPSInst_RT(ir)); |
1118 | if (!access_ok(VERIFY_WRITE, wva, sizeof(u32))) { | 1118 | if (!access_ok(wva, sizeof(u32))) { |
1119 | MIPS_FPU_EMU_INC_STATS(errors); | 1119 | MIPS_FPU_EMU_INC_STATS(errors); |
1120 | *fault_addr = wva; | 1120 | *fault_addr = wva; |
1121 | return SIGBUS; | 1121 | return SIGBUS; |
@@ -1493,7 +1493,7 @@ static int fpux_emu(struct pt_regs *xcp, struct mips_fpu_struct *ctx, | |||
1493 | xcp->regs[MIPSInst_FT(ir)]); | 1493 | xcp->regs[MIPSInst_FT(ir)]); |
1494 | 1494 | ||
1495 | MIPS_FPU_EMU_INC_STATS(loads); | 1495 | MIPS_FPU_EMU_INC_STATS(loads); |
1496 | if (!access_ok(VERIFY_READ, va, sizeof(u32))) { | 1496 | if (!access_ok(va, sizeof(u32))) { |
1497 | MIPS_FPU_EMU_INC_STATS(errors); | 1497 | MIPS_FPU_EMU_INC_STATS(errors); |
1498 | *fault_addr = va; | 1498 | *fault_addr = va; |
1499 | return SIGBUS; | 1499 | return SIGBUS; |
@@ -1513,7 +1513,7 @@ static int fpux_emu(struct pt_regs *xcp, struct mips_fpu_struct *ctx, | |||
1513 | MIPS_FPU_EMU_INC_STATS(stores); | 1513 | MIPS_FPU_EMU_INC_STATS(stores); |
1514 | 1514 | ||
1515 | SIFROMREG(val, MIPSInst_FS(ir)); | 1515 | SIFROMREG(val, MIPSInst_FS(ir)); |
1516 | if (!access_ok(VERIFY_WRITE, va, sizeof(u32))) { | 1516 | if (!access_ok(va, sizeof(u32))) { |
1517 | MIPS_FPU_EMU_INC_STATS(errors); | 1517 | MIPS_FPU_EMU_INC_STATS(errors); |
1518 | *fault_addr = va; | 1518 | *fault_addr = va; |
1519 | return SIGBUS; | 1519 | return SIGBUS; |
@@ -1590,7 +1590,7 @@ static int fpux_emu(struct pt_regs *xcp, struct mips_fpu_struct *ctx, | |||
1590 | xcp->regs[MIPSInst_FT(ir)]); | 1590 | xcp->regs[MIPSInst_FT(ir)]); |
1591 | 1591 | ||
1592 | MIPS_FPU_EMU_INC_STATS(loads); | 1592 | MIPS_FPU_EMU_INC_STATS(loads); |
1593 | if (!access_ok(VERIFY_READ, va, sizeof(u64))) { | 1593 | if (!access_ok(va, sizeof(u64))) { |
1594 | MIPS_FPU_EMU_INC_STATS(errors); | 1594 | MIPS_FPU_EMU_INC_STATS(errors); |
1595 | *fault_addr = va; | 1595 | *fault_addr = va; |
1596 | return SIGBUS; | 1596 | return SIGBUS; |
@@ -1609,7 +1609,7 @@ static int fpux_emu(struct pt_regs *xcp, struct mips_fpu_struct *ctx, | |||
1609 | 1609 | ||
1610 | MIPS_FPU_EMU_INC_STATS(stores); | 1610 | MIPS_FPU_EMU_INC_STATS(stores); |
1611 | DIFROMREG(val, MIPSInst_FS(ir)); | 1611 | DIFROMREG(val, MIPSInst_FS(ir)); |
1612 | if (!access_ok(VERIFY_WRITE, va, sizeof(u64))) { | 1612 | if (!access_ok(va, sizeof(u64))) { |
1613 | MIPS_FPU_EMU_INC_STATS(errors); | 1613 | MIPS_FPU_EMU_INC_STATS(errors); |
1614 | *fault_addr = va; | 1614 | *fault_addr = va; |
1615 | return SIGBUS; | 1615 | return SIGBUS; |
diff --git a/arch/mips/mm/cache.c b/arch/mips/mm/cache.c index 70a523151ff3..55099fbff4e6 100644 --- a/arch/mips/mm/cache.c +++ b/arch/mips/mm/cache.c | |||
@@ -76,7 +76,7 @@ SYSCALL_DEFINE3(cacheflush, unsigned long, addr, unsigned long, bytes, | |||
76 | { | 76 | { |
77 | if (bytes == 0) | 77 | if (bytes == 0) |
78 | return 0; | 78 | return 0; |
79 | if (!access_ok(VERIFY_WRITE, (void __user *) addr, bytes)) | 79 | if (!access_ok((void __user *) addr, bytes)) |
80 | return -EFAULT; | 80 | return -EFAULT; |
81 | 81 | ||
82 | __flush_icache_user_range(addr, addr + bytes); | 82 | __flush_icache_user_range(addr, addr + bytes); |
diff --git a/arch/mips/mm/gup.c b/arch/mips/mm/gup.c index 5a4875cac1ec..0d14e0d8eacf 100644 --- a/arch/mips/mm/gup.c +++ b/arch/mips/mm/gup.c | |||
@@ -195,8 +195,7 @@ int __get_user_pages_fast(unsigned long start, int nr_pages, int write, | |||
195 | addr = start; | 195 | addr = start; |
196 | len = (unsigned long) nr_pages << PAGE_SHIFT; | 196 | len = (unsigned long) nr_pages << PAGE_SHIFT; |
197 | end = start + len; | 197 | end = start + len; |
198 | if (unlikely(!access_ok(write ? VERIFY_WRITE : VERIFY_READ, | 198 | if (unlikely(!access_ok((void __user *)start, len))) |
199 | (void __user *)start, len))) | ||
200 | return 0; | 199 | return 0; |
201 | 200 | ||
202 | /* | 201 | /* |
diff --git a/arch/mips/oprofile/backtrace.c b/arch/mips/oprofile/backtrace.c index 806fb798091f..07d98ba7f49e 100644 --- a/arch/mips/oprofile/backtrace.c +++ b/arch/mips/oprofile/backtrace.c | |||
@@ -19,7 +19,7 @@ struct stackframe { | |||
19 | static inline int get_mem(unsigned long addr, unsigned long *result) | 19 | static inline int get_mem(unsigned long addr, unsigned long *result) |
20 | { | 20 | { |
21 | unsigned long *address = (unsigned long *) addr; | 21 | unsigned long *address = (unsigned long *) addr; |
22 | if (!access_ok(VERIFY_READ, address, sizeof(unsigned long))) | 22 | if (!access_ok(address, sizeof(unsigned long))) |
23 | return -1; | 23 | return -1; |
24 | if (__copy_from_user_inatomic(result, address, sizeof(unsigned long))) | 24 | if (__copy_from_user_inatomic(result, address, sizeof(unsigned long))) |
25 | return -3; | 25 | return -3; |
diff --git a/arch/mips/sibyte/common/sb_tbprof.c b/arch/mips/sibyte/common/sb_tbprof.c index 99c720be72d2..9ff26b0cd3b6 100644 --- a/arch/mips/sibyte/common/sb_tbprof.c +++ b/arch/mips/sibyte/common/sb_tbprof.c | |||
@@ -458,7 +458,7 @@ static ssize_t sbprof_tb_read(struct file *filp, char *buf, | |||
458 | char *dest = buf; | 458 | char *dest = buf; |
459 | long cur_off = *offp; | 459 | long cur_off = *offp; |
460 | 460 | ||
461 | if (!access_ok(VERIFY_WRITE, buf, size)) | 461 | if (!access_ok(buf, size)) |
462 | return -EFAULT; | 462 | return -EFAULT; |
463 | 463 | ||
464 | mutex_lock(&sbp.lock); | 464 | mutex_lock(&sbp.lock); |
diff --git a/arch/nds32/include/asm/futex.h b/arch/nds32/include/asm/futex.h index cb6cb91cfdf8..baf178bf1d0b 100644 --- a/arch/nds32/include/asm/futex.h +++ b/arch/nds32/include/asm/futex.h | |||
@@ -40,7 +40,7 @@ futex_atomic_cmpxchg_inatomic(u32 * uval, u32 __user * uaddr, | |||
40 | int ret = 0; | 40 | int ret = 0; |
41 | u32 val, tmp, flags; | 41 | u32 val, tmp, flags; |
42 | 42 | ||
43 | if (!access_ok(VERIFY_WRITE, uaddr, sizeof(u32))) | 43 | if (!access_ok(uaddr, sizeof(u32))) |
44 | return -EFAULT; | 44 | return -EFAULT; |
45 | 45 | ||
46 | smp_mb(); | 46 | smp_mb(); |
diff --git a/arch/nds32/include/asm/uaccess.h b/arch/nds32/include/asm/uaccess.h index 362a32d9bd16..53dcb49b0b12 100644 --- a/arch/nds32/include/asm/uaccess.h +++ b/arch/nds32/include/asm/uaccess.h | |||
@@ -13,9 +13,6 @@ | |||
13 | #include <asm/types.h> | 13 | #include <asm/types.h> |
14 | #include <linux/mm.h> | 14 | #include <linux/mm.h> |
15 | 15 | ||
16 | #define VERIFY_READ 0 | ||
17 | #define VERIFY_WRITE 1 | ||
18 | |||
19 | #define __asmeq(x, y) ".ifnc " x "," y " ; .err ; .endif\n\t" | 16 | #define __asmeq(x, y) ".ifnc " x "," y " ; .err ; .endif\n\t" |
20 | 17 | ||
21 | /* | 18 | /* |
@@ -53,7 +50,7 @@ static inline void set_fs(mm_segment_t fs) | |||
53 | 50 | ||
54 | #define __range_ok(addr, size) (size <= get_fs() && addr <= (get_fs() -size)) | 51 | #define __range_ok(addr, size) (size <= get_fs() && addr <= (get_fs() -size)) |
55 | 52 | ||
56 | #define access_ok(type, addr, size) \ | 53 | #define access_ok(addr, size) \ |
57 | __range_ok((unsigned long)addr, (unsigned long)size) | 54 | __range_ok((unsigned long)addr, (unsigned long)size) |
58 | /* | 55 | /* |
59 | * Single-value transfer routines. They automatically use the right | 56 | * Single-value transfer routines. They automatically use the right |
@@ -94,7 +91,7 @@ static inline void set_fs(mm_segment_t fs) | |||
94 | ({ \ | 91 | ({ \ |
95 | const __typeof__(*(ptr)) __user *__p = (ptr); \ | 92 | const __typeof__(*(ptr)) __user *__p = (ptr); \ |
96 | might_fault(); \ | 93 | might_fault(); \ |
97 | if (access_ok(VERIFY_READ, __p, sizeof(*__p))) { \ | 94 | if (access_ok(__p, sizeof(*__p))) { \ |
98 | __get_user_err((x), __p, (err)); \ | 95 | __get_user_err((x), __p, (err)); \ |
99 | } else { \ | 96 | } else { \ |
100 | (x) = 0; (err) = -EFAULT; \ | 97 | (x) = 0; (err) = -EFAULT; \ |
@@ -189,7 +186,7 @@ do { \ | |||
189 | ({ \ | 186 | ({ \ |
190 | __typeof__(*(ptr)) __user *__p = (ptr); \ | 187 | __typeof__(*(ptr)) __user *__p = (ptr); \ |
191 | might_fault(); \ | 188 | might_fault(); \ |
192 | if (access_ok(VERIFY_WRITE, __p, sizeof(*__p))) { \ | 189 | if (access_ok(__p, sizeof(*__p))) { \ |
193 | __put_user_err((x), __p, (err)); \ | 190 | __put_user_err((x), __p, (err)); \ |
194 | } else { \ | 191 | } else { \ |
195 | (err) = -EFAULT; \ | 192 | (err) = -EFAULT; \ |
@@ -279,7 +276,7 @@ extern unsigned long __arch_copy_to_user(void __user * to, const void *from, | |||
279 | #define INLINE_COPY_TO_USER | 276 | #define INLINE_COPY_TO_USER |
280 | static inline unsigned long clear_user(void __user * to, unsigned long n) | 277 | static inline unsigned long clear_user(void __user * to, unsigned long n) |
281 | { | 278 | { |
282 | if (access_ok(VERIFY_WRITE, to, n)) | 279 | if (access_ok(to, n)) |
283 | n = __arch_clear_user(to, n); | 280 | n = __arch_clear_user(to, n); |
284 | return n; | 281 | return n; |
285 | } | 282 | } |
diff --git a/arch/nds32/kernel/perf_event_cpu.c b/arch/nds32/kernel/perf_event_cpu.c index 5e00ce54d0ff..334c2a6cec23 100644 --- a/arch/nds32/kernel/perf_event_cpu.c +++ b/arch/nds32/kernel/perf_event_cpu.c | |||
@@ -1306,7 +1306,7 @@ user_backtrace(struct perf_callchain_entry_ctx *entry, unsigned long fp) | |||
1306 | (unsigned long *)(fp - (unsigned long)sizeof(buftail)); | 1306 | (unsigned long *)(fp - (unsigned long)sizeof(buftail)); |
1307 | 1307 | ||
1308 | /* Check accessibility of one struct frame_tail beyond */ | 1308 | /* Check accessibility of one struct frame_tail beyond */ |
1309 | if (!access_ok(VERIFY_READ, user_frame_tail, sizeof(buftail))) | 1309 | if (!access_ok(user_frame_tail, sizeof(buftail))) |
1310 | return 0; | 1310 | return 0; |
1311 | if (__copy_from_user_inatomic | 1311 | if (__copy_from_user_inatomic |
1312 | (&buftail, user_frame_tail, sizeof(buftail))) | 1312 | (&buftail, user_frame_tail, sizeof(buftail))) |
@@ -1332,7 +1332,7 @@ user_backtrace_opt_size(struct perf_callchain_entry_ctx *entry, | |||
1332 | (unsigned long *)(fp - (unsigned long)sizeof(buftail)); | 1332 | (unsigned long *)(fp - (unsigned long)sizeof(buftail)); |
1333 | 1333 | ||
1334 | /* Check accessibility of one struct frame_tail beyond */ | 1334 | /* Check accessibility of one struct frame_tail beyond */ |
1335 | if (!access_ok(VERIFY_READ, user_frame_tail, sizeof(buftail))) | 1335 | if (!access_ok(user_frame_tail, sizeof(buftail))) |
1336 | return 0; | 1336 | return 0; |
1337 | if (__copy_from_user_inatomic | 1337 | if (__copy_from_user_inatomic |
1338 | (&buftail, user_frame_tail, sizeof(buftail))) | 1338 | (&buftail, user_frame_tail, sizeof(buftail))) |
@@ -1386,7 +1386,7 @@ perf_callchain_user(struct perf_callchain_entry_ctx *entry, | |||
1386 | user_frame_tail = | 1386 | user_frame_tail = |
1387 | (unsigned long *)(fp - (unsigned long)sizeof(fp)); | 1387 | (unsigned long *)(fp - (unsigned long)sizeof(fp)); |
1388 | 1388 | ||
1389 | if (!access_ok(VERIFY_READ, user_frame_tail, sizeof(fp))) | 1389 | if (!access_ok(user_frame_tail, sizeof(fp))) |
1390 | return; | 1390 | return; |
1391 | 1391 | ||
1392 | if (__copy_from_user_inatomic | 1392 | if (__copy_from_user_inatomic |
@@ -1406,8 +1406,7 @@ perf_callchain_user(struct perf_callchain_entry_ctx *entry, | |||
1406 | (unsigned long *)(fp - | 1406 | (unsigned long *)(fp - |
1407 | (unsigned long)sizeof(buftail)); | 1407 | (unsigned long)sizeof(buftail)); |
1408 | 1408 | ||
1409 | if (!access_ok | 1409 | if (!access_ok(user_frame_tail, sizeof(buftail))) |
1410 | (VERIFY_READ, user_frame_tail, sizeof(buftail))) | ||
1411 | return; | 1410 | return; |
1412 | 1411 | ||
1413 | if (__copy_from_user_inatomic | 1412 | if (__copy_from_user_inatomic |
@@ -1424,7 +1423,7 @@ perf_callchain_user(struct perf_callchain_entry_ctx *entry, | |||
1424 | (unsigned long *)(fp - (unsigned long) | 1423 | (unsigned long *)(fp - (unsigned long) |
1425 | sizeof(buftail_opt_size)); | 1424 | sizeof(buftail_opt_size)); |
1426 | 1425 | ||
1427 | if (!access_ok(VERIFY_READ, user_frame_tail, | 1426 | if (!access_ok(user_frame_tail, |
1428 | sizeof(buftail_opt_size))) | 1427 | sizeof(buftail_opt_size))) |
1429 | return; | 1428 | return; |
1430 | 1429 | ||
diff --git a/arch/nds32/kernel/signal.c b/arch/nds32/kernel/signal.c index 5b5be082cfa4..5f7660aa2d68 100644 --- a/arch/nds32/kernel/signal.c +++ b/arch/nds32/kernel/signal.c | |||
@@ -151,7 +151,7 @@ asmlinkage long sys_rt_sigreturn(struct pt_regs *regs) | |||
151 | 151 | ||
152 | frame = (struct rt_sigframe __user *)regs->sp; | 152 | frame = (struct rt_sigframe __user *)regs->sp; |
153 | 153 | ||
154 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 154 | if (!access_ok(frame, sizeof(*frame))) |
155 | goto badframe; | 155 | goto badframe; |
156 | 156 | ||
157 | if (restore_sigframe(regs, frame)) | 157 | if (restore_sigframe(regs, frame)) |
@@ -275,7 +275,7 @@ setup_rt_frame(struct ksignal *ksig, sigset_t * set, struct pt_regs *regs) | |||
275 | get_sigframe(ksig, regs, sizeof(*frame)); | 275 | get_sigframe(ksig, regs, sizeof(*frame)); |
276 | int err = 0; | 276 | int err = 0; |
277 | 277 | ||
278 | if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame))) | 278 | if (!access_ok(frame, sizeof(*frame))) |
279 | return -EFAULT; | 279 | return -EFAULT; |
280 | 280 | ||
281 | __put_user_error(0, &frame->uc.uc_flags, err); | 281 | __put_user_error(0, &frame->uc.uc_flags, err); |
diff --git a/arch/nds32/mm/alignment.c b/arch/nds32/mm/alignment.c index e1aed9dc692d..c8b9061a2ee3 100644 --- a/arch/nds32/mm/alignment.c +++ b/arch/nds32/mm/alignment.c | |||
@@ -289,13 +289,13 @@ static inline int do_16(unsigned long inst, struct pt_regs *regs) | |||
289 | unaligned_addr += shift; | 289 | unaligned_addr += shift; |
290 | 290 | ||
291 | if (load) { | 291 | if (load) { |
292 | if (!access_ok(VERIFY_READ, (void *)unaligned_addr, len)) | 292 | if (!access_ok((void *)unaligned_addr, len)) |
293 | return -EACCES; | 293 | return -EACCES; |
294 | 294 | ||
295 | get_data(unaligned_addr, &target_val, len); | 295 | get_data(unaligned_addr, &target_val, len); |
296 | *idx_to_addr(regs, target_idx) = target_val; | 296 | *idx_to_addr(regs, target_idx) = target_val; |
297 | } else { | 297 | } else { |
298 | if (!access_ok(VERIFY_WRITE, (void *)unaligned_addr, len)) | 298 | if (!access_ok((void *)unaligned_addr, len)) |
299 | return -EACCES; | 299 | return -EACCES; |
300 | target_val = *idx_to_addr(regs, target_idx); | 300 | target_val = *idx_to_addr(regs, target_idx); |
301 | set_data((void *)unaligned_addr, target_val, len); | 301 | set_data((void *)unaligned_addr, target_val, len); |
@@ -479,7 +479,7 @@ static inline int do_32(unsigned long inst, struct pt_regs *regs) | |||
479 | 479 | ||
480 | if (load) { | 480 | if (load) { |
481 | 481 | ||
482 | if (!access_ok(VERIFY_READ, (void *)unaligned_addr, len)) | 482 | if (!access_ok((void *)unaligned_addr, len)) |
483 | return -EACCES; | 483 | return -EACCES; |
484 | 484 | ||
485 | get_data(unaligned_addr, &target_val, len); | 485 | get_data(unaligned_addr, &target_val, len); |
@@ -491,7 +491,7 @@ static inline int do_32(unsigned long inst, struct pt_regs *regs) | |||
491 | *idx_to_addr(regs, RT(inst)) = target_val; | 491 | *idx_to_addr(regs, RT(inst)) = target_val; |
492 | } else { | 492 | } else { |
493 | 493 | ||
494 | if (!access_ok(VERIFY_WRITE, (void *)unaligned_addr, len)) | 494 | if (!access_ok((void *)unaligned_addr, len)) |
495 | return -EACCES; | 495 | return -EACCES; |
496 | 496 | ||
497 | target_val = *idx_to_addr(regs, RT(inst)); | 497 | target_val = *idx_to_addr(regs, RT(inst)); |
diff --git a/arch/nios2/include/asm/uaccess.h b/arch/nios2/include/asm/uaccess.h index dfa3c7cb30b4..e0ea10806491 100644 --- a/arch/nios2/include/asm/uaccess.h +++ b/arch/nios2/include/asm/uaccess.h | |||
@@ -37,7 +37,7 @@ | |||
37 | (((signed long)(((long)get_fs().seg) & \ | 37 | (((signed long)(((long)get_fs().seg) & \ |
38 | ((long)(addr) | (((long)(addr)) + (len)) | (len)))) == 0) | 38 | ((long)(addr) | (((long)(addr)) + (len)) | (len)))) == 0) |
39 | 39 | ||
40 | #define access_ok(type, addr, len) \ | 40 | #define access_ok(addr, len) \ |
41 | likely(__access_ok((unsigned long)(addr), (unsigned long)(len))) | 41 | likely(__access_ok((unsigned long)(addr), (unsigned long)(len))) |
42 | 42 | ||
43 | # define __EX_TABLE_SECTION ".section __ex_table,\"a\"\n" | 43 | # define __EX_TABLE_SECTION ".section __ex_table,\"a\"\n" |
@@ -70,7 +70,7 @@ static inline unsigned long __must_check __clear_user(void __user *to, | |||
70 | static inline unsigned long __must_check clear_user(void __user *to, | 70 | static inline unsigned long __must_check clear_user(void __user *to, |
71 | unsigned long n) | 71 | unsigned long n) |
72 | { | 72 | { |
73 | if (!access_ok(VERIFY_WRITE, to, n)) | 73 | if (!access_ok(to, n)) |
74 | return n; | 74 | return n; |
75 | return __clear_user(to, n); | 75 | return __clear_user(to, n); |
76 | } | 76 | } |
@@ -142,7 +142,7 @@ do { \ | |||
142 | long __gu_err = -EFAULT; \ | 142 | long __gu_err = -EFAULT; \ |
143 | const __typeof__(*(ptr)) __user *__gu_ptr = (ptr); \ | 143 | const __typeof__(*(ptr)) __user *__gu_ptr = (ptr); \ |
144 | unsigned long __gu_val = 0; \ | 144 | unsigned long __gu_val = 0; \ |
145 | if (access_ok(VERIFY_READ, __gu_ptr, sizeof(*__gu_ptr))) \ | 145 | if (access_ok( __gu_ptr, sizeof(*__gu_ptr))) \ |
146 | __get_user_common(__gu_val, sizeof(*__gu_ptr), \ | 146 | __get_user_common(__gu_val, sizeof(*__gu_ptr), \ |
147 | __gu_ptr, __gu_err); \ | 147 | __gu_ptr, __gu_err); \ |
148 | (x) = (__force __typeof__(x))__gu_val; \ | 148 | (x) = (__force __typeof__(x))__gu_val; \ |
@@ -168,7 +168,7 @@ do { \ | |||
168 | long __pu_err = -EFAULT; \ | 168 | long __pu_err = -EFAULT; \ |
169 | __typeof__(*(ptr)) __user *__pu_ptr = (ptr); \ | 169 | __typeof__(*(ptr)) __user *__pu_ptr = (ptr); \ |
170 | __typeof__(*(ptr)) __pu_val = (__typeof(*ptr))(x); \ | 170 | __typeof__(*(ptr)) __pu_val = (__typeof(*ptr))(x); \ |
171 | if (access_ok(VERIFY_WRITE, __pu_ptr, sizeof(*__pu_ptr))) { \ | 171 | if (access_ok(__pu_ptr, sizeof(*__pu_ptr))) { \ |
172 | switch (sizeof(*__pu_ptr)) { \ | 172 | switch (sizeof(*__pu_ptr)) { \ |
173 | case 1: \ | 173 | case 1: \ |
174 | __put_user_asm(__pu_val, "stb", __pu_ptr, __pu_err); \ | 174 | __put_user_asm(__pu_val, "stb", __pu_ptr, __pu_err); \ |
diff --git a/arch/nios2/kernel/signal.c b/arch/nios2/kernel/signal.c index 20662b0f6c9e..4a81876b6086 100644 --- a/arch/nios2/kernel/signal.c +++ b/arch/nios2/kernel/signal.c | |||
@@ -106,7 +106,7 @@ asmlinkage int do_rt_sigreturn(struct switch_stack *sw) | |||
106 | sigset_t set; | 106 | sigset_t set; |
107 | int rval; | 107 | int rval; |
108 | 108 | ||
109 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 109 | if (!access_ok(frame, sizeof(*frame))) |
110 | goto badframe; | 110 | goto badframe; |
111 | 111 | ||
112 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) | 112 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) |
diff --git a/arch/openrisc/include/asm/futex.h b/arch/openrisc/include/asm/futex.h index 618da4a1bffb..fe894e6331ae 100644 --- a/arch/openrisc/include/asm/futex.h +++ b/arch/openrisc/include/asm/futex.h | |||
@@ -72,7 +72,7 @@ futex_atomic_cmpxchg_inatomic(u32 *uval, u32 __user *uaddr, | |||
72 | int ret = 0; | 72 | int ret = 0; |
73 | u32 prev; | 73 | u32 prev; |
74 | 74 | ||
75 | if (!access_ok(VERIFY_WRITE, uaddr, sizeof(u32))) | 75 | if (!access_ok(uaddr, sizeof(u32))) |
76 | return -EFAULT; | 76 | return -EFAULT; |
77 | 77 | ||
78 | __asm__ __volatile__ ( \ | 78 | __asm__ __volatile__ ( \ |
diff --git a/arch/openrisc/include/asm/uaccess.h b/arch/openrisc/include/asm/uaccess.h index bbf5c79cce7a..bc8191a34db7 100644 --- a/arch/openrisc/include/asm/uaccess.h +++ b/arch/openrisc/include/asm/uaccess.h | |||
@@ -58,7 +58,7 @@ | |||
58 | /* Ensure that addr is below task's addr_limit */ | 58 | /* Ensure that addr is below task's addr_limit */ |
59 | #define __addr_ok(addr) ((unsigned long) addr < get_fs()) | 59 | #define __addr_ok(addr) ((unsigned long) addr < get_fs()) |
60 | 60 | ||
61 | #define access_ok(type, addr, size) \ | 61 | #define access_ok(addr, size) \ |
62 | __range_ok((unsigned long)addr, (unsigned long)size) | 62 | __range_ok((unsigned long)addr, (unsigned long)size) |
63 | 63 | ||
64 | /* | 64 | /* |
@@ -102,7 +102,7 @@ extern long __put_user_bad(void); | |||
102 | ({ \ | 102 | ({ \ |
103 | long __pu_err = -EFAULT; \ | 103 | long __pu_err = -EFAULT; \ |
104 | __typeof__(*(ptr)) *__pu_addr = (ptr); \ | 104 | __typeof__(*(ptr)) *__pu_addr = (ptr); \ |
105 | if (access_ok(VERIFY_WRITE, __pu_addr, size)) \ | 105 | if (access_ok(__pu_addr, size)) \ |
106 | __put_user_size((x), __pu_addr, (size), __pu_err); \ | 106 | __put_user_size((x), __pu_addr, (size), __pu_err); \ |
107 | __pu_err; \ | 107 | __pu_err; \ |
108 | }) | 108 | }) |
@@ -175,7 +175,7 @@ struct __large_struct { | |||
175 | ({ \ | 175 | ({ \ |
176 | long __gu_err = -EFAULT, __gu_val = 0; \ | 176 | long __gu_err = -EFAULT, __gu_val = 0; \ |
177 | const __typeof__(*(ptr)) * __gu_addr = (ptr); \ | 177 | const __typeof__(*(ptr)) * __gu_addr = (ptr); \ |
178 | if (access_ok(VERIFY_READ, __gu_addr, size)) \ | 178 | if (access_ok(__gu_addr, size)) \ |
179 | __get_user_size(__gu_val, __gu_addr, (size), __gu_err); \ | 179 | __get_user_size(__gu_val, __gu_addr, (size), __gu_err); \ |
180 | (x) = (__force __typeof__(*(ptr)))__gu_val; \ | 180 | (x) = (__force __typeof__(*(ptr)))__gu_val; \ |
181 | __gu_err; \ | 181 | __gu_err; \ |
@@ -254,7 +254,7 @@ extern unsigned long __clear_user(void *addr, unsigned long size); | |||
254 | static inline __must_check unsigned long | 254 | static inline __must_check unsigned long |
255 | clear_user(void *addr, unsigned long size) | 255 | clear_user(void *addr, unsigned long size) |
256 | { | 256 | { |
257 | if (likely(access_ok(VERIFY_WRITE, addr, size))) | 257 | if (likely(access_ok(addr, size))) |
258 | size = __clear_user(addr, size); | 258 | size = __clear_user(addr, size); |
259 | return size; | 259 | return size; |
260 | } | 260 | } |
diff --git a/arch/openrisc/kernel/signal.c b/arch/openrisc/kernel/signal.c index 265f10fb3930..5ac9d3b1d615 100644 --- a/arch/openrisc/kernel/signal.c +++ b/arch/openrisc/kernel/signal.c | |||
@@ -50,7 +50,7 @@ static int restore_sigcontext(struct pt_regs *regs, | |||
50 | 50 | ||
51 | /* | 51 | /* |
52 | * Restore the regs from &sc->regs. | 52 | * Restore the regs from &sc->regs. |
53 | * (sc is already checked for VERIFY_READ since the sigframe was | 53 | * (sc is already checked since the sigframe was |
54 | * checked in sys_sigreturn previously) | 54 | * checked in sys_sigreturn previously) |
55 | */ | 55 | */ |
56 | err |= __copy_from_user(regs, sc->regs.gpr, 32 * sizeof(unsigned long)); | 56 | err |= __copy_from_user(regs, sc->regs.gpr, 32 * sizeof(unsigned long)); |
@@ -83,7 +83,7 @@ asmlinkage long _sys_rt_sigreturn(struct pt_regs *regs) | |||
83 | if (((long)frame) & 3) | 83 | if (((long)frame) & 3) |
84 | goto badframe; | 84 | goto badframe; |
85 | 85 | ||
86 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 86 | if (!access_ok(frame, sizeof(*frame))) |
87 | goto badframe; | 87 | goto badframe; |
88 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) | 88 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) |
89 | goto badframe; | 89 | goto badframe; |
@@ -161,7 +161,7 @@ static int setup_rt_frame(struct ksignal *ksig, sigset_t *set, | |||
161 | 161 | ||
162 | frame = get_sigframe(ksig, regs, sizeof(*frame)); | 162 | frame = get_sigframe(ksig, regs, sizeof(*frame)); |
163 | 163 | ||
164 | if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame))) | 164 | if (!access_ok(frame, sizeof(*frame))) |
165 | return -EFAULT; | 165 | return -EFAULT; |
166 | 166 | ||
167 | /* Create siginfo. */ | 167 | /* Create siginfo. */ |
diff --git a/arch/parisc/include/asm/futex.h b/arch/parisc/include/asm/futex.h index cf7ba058f619..d2c3e4106851 100644 --- a/arch/parisc/include/asm/futex.h +++ b/arch/parisc/include/asm/futex.h | |||
@@ -95,7 +95,7 @@ futex_atomic_cmpxchg_inatomic(u32 *uval, u32 __user *uaddr, | |||
95 | if (uaccess_kernel() && !uaddr) | 95 | if (uaccess_kernel() && !uaddr) |
96 | return -EFAULT; | 96 | return -EFAULT; |
97 | 97 | ||
98 | if (!access_ok(VERIFY_WRITE, uaddr, sizeof(u32))) | 98 | if (!access_ok(uaddr, sizeof(u32))) |
99 | return -EFAULT; | 99 | return -EFAULT; |
100 | 100 | ||
101 | /* HPPA has no cmpxchg in hardware and therefore the | 101 | /* HPPA has no cmpxchg in hardware and therefore the |
diff --git a/arch/parisc/include/asm/uaccess.h b/arch/parisc/include/asm/uaccess.h index ea70e36ce6af..30ac2865ea73 100644 --- a/arch/parisc/include/asm/uaccess.h +++ b/arch/parisc/include/asm/uaccess.h | |||
@@ -27,7 +27,7 @@ | |||
27 | * that put_user is the same as __put_user, etc. | 27 | * that put_user is the same as __put_user, etc. |
28 | */ | 28 | */ |
29 | 29 | ||
30 | #define access_ok(type, uaddr, size) \ | 30 | #define access_ok(uaddr, size) \ |
31 | ( (uaddr) == (uaddr) ) | 31 | ( (uaddr) == (uaddr) ) |
32 | 32 | ||
33 | #define put_user __put_user | 33 | #define put_user __put_user |
diff --git a/arch/powerpc/include/asm/futex.h b/arch/powerpc/include/asm/futex.h index 94542776a62d..88b38b37c21b 100644 --- a/arch/powerpc/include/asm/futex.h +++ b/arch/powerpc/include/asm/futex.h | |||
@@ -72,7 +72,7 @@ futex_atomic_cmpxchg_inatomic(u32 *uval, u32 __user *uaddr, | |||
72 | int ret = 0; | 72 | int ret = 0; |
73 | u32 prev; | 73 | u32 prev; |
74 | 74 | ||
75 | if (!access_ok(VERIFY_WRITE, uaddr, sizeof(u32))) | 75 | if (!access_ok(uaddr, sizeof(u32))) |
76 | return -EFAULT; | 76 | return -EFAULT; |
77 | 77 | ||
78 | __asm__ __volatile__ ( | 78 | __asm__ __volatile__ ( |
diff --git a/arch/powerpc/include/asm/uaccess.h b/arch/powerpc/include/asm/uaccess.h index ebc0b916dcf9..e3a731793ea2 100644 --- a/arch/powerpc/include/asm/uaccess.h +++ b/arch/powerpc/include/asm/uaccess.h | |||
@@ -62,8 +62,8 @@ static inline int __access_ok(unsigned long addr, unsigned long size, | |||
62 | 62 | ||
63 | #endif | 63 | #endif |
64 | 64 | ||
65 | #define access_ok(type, addr, size) \ | 65 | #define access_ok(addr, size) \ |
66 | (__chk_user_ptr(addr), (void)(type), \ | 66 | (__chk_user_ptr(addr), \ |
67 | __access_ok((__force unsigned long)(addr), (size), get_fs())) | 67 | __access_ok((__force unsigned long)(addr), (size), get_fs())) |
68 | 68 | ||
69 | /* | 69 | /* |
@@ -166,7 +166,7 @@ do { \ | |||
166 | long __pu_err = -EFAULT; \ | 166 | long __pu_err = -EFAULT; \ |
167 | __typeof__(*(ptr)) __user *__pu_addr = (ptr); \ | 167 | __typeof__(*(ptr)) __user *__pu_addr = (ptr); \ |
168 | might_fault(); \ | 168 | might_fault(); \ |
169 | if (access_ok(VERIFY_WRITE, __pu_addr, size)) \ | 169 | if (access_ok(__pu_addr, size)) \ |
170 | __put_user_size((x), __pu_addr, (size), __pu_err); \ | 170 | __put_user_size((x), __pu_addr, (size), __pu_err); \ |
171 | __pu_err; \ | 171 | __pu_err; \ |
172 | }) | 172 | }) |
@@ -276,7 +276,7 @@ do { \ | |||
276 | __long_type(*(ptr)) __gu_val = 0; \ | 276 | __long_type(*(ptr)) __gu_val = 0; \ |
277 | __typeof__(*(ptr)) __user *__gu_addr = (ptr); \ | 277 | __typeof__(*(ptr)) __user *__gu_addr = (ptr); \ |
278 | might_fault(); \ | 278 | might_fault(); \ |
279 | if (access_ok(VERIFY_READ, __gu_addr, (size))) { \ | 279 | if (access_ok(__gu_addr, (size))) { \ |
280 | barrier_nospec(); \ | 280 | barrier_nospec(); \ |
281 | __get_user_size(__gu_val, __gu_addr, (size), __gu_err); \ | 281 | __get_user_size(__gu_val, __gu_addr, (size), __gu_err); \ |
282 | } \ | 282 | } \ |
@@ -374,7 +374,7 @@ extern unsigned long __clear_user(void __user *addr, unsigned long size); | |||
374 | static inline unsigned long clear_user(void __user *addr, unsigned long size) | 374 | static inline unsigned long clear_user(void __user *addr, unsigned long size) |
375 | { | 375 | { |
376 | might_fault(); | 376 | might_fault(); |
377 | if (likely(access_ok(VERIFY_WRITE, addr, size))) | 377 | if (likely(access_ok(addr, size))) |
378 | return __clear_user(addr, size); | 378 | return __clear_user(addr, size); |
379 | return size; | 379 | return size; |
380 | } | 380 | } |
diff --git a/arch/powerpc/kernel/align.c b/arch/powerpc/kernel/align.c index 11550a3d1ac2..0d1b6370bae0 100644 --- a/arch/powerpc/kernel/align.c +++ b/arch/powerpc/kernel/align.c | |||
@@ -131,8 +131,7 @@ static int emulate_spe(struct pt_regs *regs, unsigned int reg, | |||
131 | 131 | ||
132 | /* Verify the address of the operand */ | 132 | /* Verify the address of the operand */ |
133 | if (unlikely(user_mode(regs) && | 133 | if (unlikely(user_mode(regs) && |
134 | !access_ok((flags & ST ? VERIFY_WRITE : VERIFY_READ), | 134 | !access_ok(addr, nb))) |
135 | addr, nb))) | ||
136 | return -EFAULT; | 135 | return -EFAULT; |
137 | 136 | ||
138 | /* userland only */ | 137 | /* userland only */ |
diff --git a/arch/powerpc/kernel/rtas_flash.c b/arch/powerpc/kernel/rtas_flash.c index 10fabae2574d..8246f437bbc6 100644 --- a/arch/powerpc/kernel/rtas_flash.c +++ b/arch/powerpc/kernel/rtas_flash.c | |||
@@ -523,7 +523,7 @@ static ssize_t validate_flash_write(struct file *file, const char __user *buf, | |||
523 | args_buf->status = VALIDATE_INCOMPLETE; | 523 | args_buf->status = VALIDATE_INCOMPLETE; |
524 | } | 524 | } |
525 | 525 | ||
526 | if (!access_ok(VERIFY_READ, buf, count)) { | 526 | if (!access_ok(buf, count)) { |
527 | rc = -EFAULT; | 527 | rc = -EFAULT; |
528 | goto done; | 528 | goto done; |
529 | } | 529 | } |
diff --git a/arch/powerpc/kernel/rtasd.c b/arch/powerpc/kernel/rtasd.c index 38cadae4ca4f..8a1746d755c9 100644 --- a/arch/powerpc/kernel/rtasd.c +++ b/arch/powerpc/kernel/rtasd.c | |||
@@ -335,7 +335,7 @@ static ssize_t rtas_log_read(struct file * file, char __user * buf, | |||
335 | 335 | ||
336 | count = rtas_error_log_buffer_max; | 336 | count = rtas_error_log_buffer_max; |
337 | 337 | ||
338 | if (!access_ok(VERIFY_WRITE, buf, count)) | 338 | if (!access_ok(buf, count)) |
339 | return -EFAULT; | 339 | return -EFAULT; |
340 | 340 | ||
341 | tmp = kmalloc(count, GFP_KERNEL); | 341 | tmp = kmalloc(count, GFP_KERNEL); |
diff --git a/arch/powerpc/kernel/signal.c b/arch/powerpc/kernel/signal.c index b3e8db376ecd..e6c30cee6abf 100644 --- a/arch/powerpc/kernel/signal.c +++ b/arch/powerpc/kernel/signal.c | |||
@@ -44,7 +44,7 @@ void __user *get_sigframe(struct ksignal *ksig, unsigned long sp, | |||
44 | newsp = (oldsp - frame_size) & ~0xFUL; | 44 | newsp = (oldsp - frame_size) & ~0xFUL; |
45 | 45 | ||
46 | /* Check access */ | 46 | /* Check access */ |
47 | if (!access_ok(VERIFY_WRITE, (void __user *)newsp, oldsp - newsp)) | 47 | if (!access_ok((void __user *)newsp, oldsp - newsp)) |
48 | return NULL; | 48 | return NULL; |
49 | 49 | ||
50 | return (void __user *)newsp; | 50 | return (void __user *)newsp; |
diff --git a/arch/powerpc/kernel/signal_32.c b/arch/powerpc/kernel/signal_32.c index 2d47cc79e5b3..ede4f04281ae 100644 --- a/arch/powerpc/kernel/signal_32.c +++ b/arch/powerpc/kernel/signal_32.c | |||
@@ -1017,7 +1017,7 @@ static int do_setcontext(struct ucontext __user *ucp, struct pt_regs *regs, int | |||
1017 | #else | 1017 | #else |
1018 | if (__get_user(mcp, &ucp->uc_regs)) | 1018 | if (__get_user(mcp, &ucp->uc_regs)) |
1019 | return -EFAULT; | 1019 | return -EFAULT; |
1020 | if (!access_ok(VERIFY_READ, mcp, sizeof(*mcp))) | 1020 | if (!access_ok(mcp, sizeof(*mcp))) |
1021 | return -EFAULT; | 1021 | return -EFAULT; |
1022 | #endif | 1022 | #endif |
1023 | set_current_blocked(&set); | 1023 | set_current_blocked(&set); |
@@ -1120,7 +1120,7 @@ SYSCALL_DEFINE3(swapcontext, struct ucontext __user *, old_ctx, | |||
1120 | */ | 1120 | */ |
1121 | mctx = (struct mcontext __user *) | 1121 | mctx = (struct mcontext __user *) |
1122 | ((unsigned long) &old_ctx->uc_mcontext & ~0xfUL); | 1122 | ((unsigned long) &old_ctx->uc_mcontext & ~0xfUL); |
1123 | if (!access_ok(VERIFY_WRITE, old_ctx, ctx_size) | 1123 | if (!access_ok(old_ctx, ctx_size) |
1124 | || save_user_regs(regs, mctx, NULL, 0, ctx_has_vsx_region) | 1124 | || save_user_regs(regs, mctx, NULL, 0, ctx_has_vsx_region) |
1125 | || put_sigset_t(&old_ctx->uc_sigmask, ¤t->blocked) | 1125 | || put_sigset_t(&old_ctx->uc_sigmask, ¤t->blocked) |
1126 | || __put_user(to_user_ptr(mctx), &old_ctx->uc_regs)) | 1126 | || __put_user(to_user_ptr(mctx), &old_ctx->uc_regs)) |
@@ -1128,7 +1128,7 @@ SYSCALL_DEFINE3(swapcontext, struct ucontext __user *, old_ctx, | |||
1128 | } | 1128 | } |
1129 | if (new_ctx == NULL) | 1129 | if (new_ctx == NULL) |
1130 | return 0; | 1130 | return 0; |
1131 | if (!access_ok(VERIFY_READ, new_ctx, ctx_size) || | 1131 | if (!access_ok(new_ctx, ctx_size) || |
1132 | fault_in_pages_readable((u8 __user *)new_ctx, ctx_size)) | 1132 | fault_in_pages_readable((u8 __user *)new_ctx, ctx_size)) |
1133 | return -EFAULT; | 1133 | return -EFAULT; |
1134 | 1134 | ||
@@ -1169,7 +1169,7 @@ SYSCALL_DEFINE0(rt_sigreturn) | |||
1169 | 1169 | ||
1170 | rt_sf = (struct rt_sigframe __user *) | 1170 | rt_sf = (struct rt_sigframe __user *) |
1171 | (regs->gpr[1] + __SIGNAL_FRAMESIZE + 16); | 1171 | (regs->gpr[1] + __SIGNAL_FRAMESIZE + 16); |
1172 | if (!access_ok(VERIFY_READ, rt_sf, sizeof(*rt_sf))) | 1172 | if (!access_ok(rt_sf, sizeof(*rt_sf))) |
1173 | goto bad; | 1173 | goto bad; |
1174 | 1174 | ||
1175 | #ifdef CONFIG_PPC_TRANSACTIONAL_MEM | 1175 | #ifdef CONFIG_PPC_TRANSACTIONAL_MEM |
@@ -1315,7 +1315,7 @@ SYSCALL_DEFINE3(debug_setcontext, struct ucontext __user *, ctx, | |||
1315 | current->thread.debug.dbcr0 = new_dbcr0; | 1315 | current->thread.debug.dbcr0 = new_dbcr0; |
1316 | #endif | 1316 | #endif |
1317 | 1317 | ||
1318 | if (!access_ok(VERIFY_READ, ctx, sizeof(*ctx)) || | 1318 | if (!access_ok(ctx, sizeof(*ctx)) || |
1319 | fault_in_pages_readable((u8 __user *)ctx, sizeof(*ctx))) | 1319 | fault_in_pages_readable((u8 __user *)ctx, sizeof(*ctx))) |
1320 | return -EFAULT; | 1320 | return -EFAULT; |
1321 | 1321 | ||
@@ -1500,7 +1500,7 @@ SYSCALL_DEFINE0(sigreturn) | |||
1500 | { | 1500 | { |
1501 | sr = (struct mcontext __user *)from_user_ptr(sigctx.regs); | 1501 | sr = (struct mcontext __user *)from_user_ptr(sigctx.regs); |
1502 | addr = sr; | 1502 | addr = sr; |
1503 | if (!access_ok(VERIFY_READ, sr, sizeof(*sr)) | 1503 | if (!access_ok(sr, sizeof(*sr)) |
1504 | || restore_user_regs(regs, sr, 1)) | 1504 | || restore_user_regs(regs, sr, 1)) |
1505 | goto badframe; | 1505 | goto badframe; |
1506 | } | 1506 | } |
diff --git a/arch/powerpc/kernel/signal_64.c b/arch/powerpc/kernel/signal_64.c index 0935fe6c282a..bd5e6834ca69 100644 --- a/arch/powerpc/kernel/signal_64.c +++ b/arch/powerpc/kernel/signal_64.c | |||
@@ -383,7 +383,7 @@ static long restore_sigcontext(struct task_struct *tsk, sigset_t *set, int sig, | |||
383 | err |= __get_user(v_regs, &sc->v_regs); | 383 | err |= __get_user(v_regs, &sc->v_regs); |
384 | if (err) | 384 | if (err) |
385 | return err; | 385 | return err; |
386 | if (v_regs && !access_ok(VERIFY_READ, v_regs, 34 * sizeof(vector128))) | 386 | if (v_regs && !access_ok(v_regs, 34 * sizeof(vector128))) |
387 | return -EFAULT; | 387 | return -EFAULT; |
388 | /* Copy 33 vec registers (vr0..31 and vscr) from the stack */ | 388 | /* Copy 33 vec registers (vr0..31 and vscr) from the stack */ |
389 | if (v_regs != NULL && (msr & MSR_VEC) != 0) { | 389 | if (v_regs != NULL && (msr & MSR_VEC) != 0) { |
@@ -502,10 +502,9 @@ static long restore_tm_sigcontexts(struct task_struct *tsk, | |||
502 | err |= __get_user(tm_v_regs, &tm_sc->v_regs); | 502 | err |= __get_user(tm_v_regs, &tm_sc->v_regs); |
503 | if (err) | 503 | if (err) |
504 | return err; | 504 | return err; |
505 | if (v_regs && !access_ok(VERIFY_READ, v_regs, 34 * sizeof(vector128))) | 505 | if (v_regs && !access_ok(v_regs, 34 * sizeof(vector128))) |
506 | return -EFAULT; | 506 | return -EFAULT; |
507 | if (tm_v_regs && !access_ok(VERIFY_READ, | 507 | if (tm_v_regs && !access_ok(tm_v_regs, 34 * sizeof(vector128))) |
508 | tm_v_regs, 34 * sizeof(vector128))) | ||
509 | return -EFAULT; | 508 | return -EFAULT; |
510 | /* Copy 33 vec registers (vr0..31 and vscr) from the stack */ | 509 | /* Copy 33 vec registers (vr0..31 and vscr) from the stack */ |
511 | if (v_regs != NULL && tm_v_regs != NULL && (msr & MSR_VEC) != 0) { | 510 | if (v_regs != NULL && tm_v_regs != NULL && (msr & MSR_VEC) != 0) { |
@@ -671,7 +670,7 @@ SYSCALL_DEFINE3(swapcontext, struct ucontext __user *, old_ctx, | |||
671 | ctx_has_vsx_region = 1; | 670 | ctx_has_vsx_region = 1; |
672 | 671 | ||
673 | if (old_ctx != NULL) { | 672 | if (old_ctx != NULL) { |
674 | if (!access_ok(VERIFY_WRITE, old_ctx, ctx_size) | 673 | if (!access_ok(old_ctx, ctx_size) |
675 | || setup_sigcontext(&old_ctx->uc_mcontext, current, 0, NULL, 0, | 674 | || setup_sigcontext(&old_ctx->uc_mcontext, current, 0, NULL, 0, |
676 | ctx_has_vsx_region) | 675 | ctx_has_vsx_region) |
677 | || __copy_to_user(&old_ctx->uc_sigmask, | 676 | || __copy_to_user(&old_ctx->uc_sigmask, |
@@ -680,7 +679,7 @@ SYSCALL_DEFINE3(swapcontext, struct ucontext __user *, old_ctx, | |||
680 | } | 679 | } |
681 | if (new_ctx == NULL) | 680 | if (new_ctx == NULL) |
682 | return 0; | 681 | return 0; |
683 | if (!access_ok(VERIFY_READ, new_ctx, ctx_size) | 682 | if (!access_ok(new_ctx, ctx_size) |
684 | || __get_user(tmp, (u8 __user *) new_ctx) | 683 | || __get_user(tmp, (u8 __user *) new_ctx) |
685 | || __get_user(tmp, (u8 __user *) new_ctx + ctx_size - 1)) | 684 | || __get_user(tmp, (u8 __user *) new_ctx + ctx_size - 1)) |
686 | return -EFAULT; | 685 | return -EFAULT; |
@@ -725,7 +724,7 @@ SYSCALL_DEFINE0(rt_sigreturn) | |||
725 | /* Always make any pending restarted system calls return -EINTR */ | 724 | /* Always make any pending restarted system calls return -EINTR */ |
726 | current->restart_block.fn = do_no_restart_syscall; | 725 | current->restart_block.fn = do_no_restart_syscall; |
727 | 726 | ||
728 | if (!access_ok(VERIFY_READ, uc, sizeof(*uc))) | 727 | if (!access_ok(uc, sizeof(*uc))) |
729 | goto badframe; | 728 | goto badframe; |
730 | 729 | ||
731 | if (__copy_from_user(&set, &uc->uc_sigmask, sizeof(set))) | 730 | if (__copy_from_user(&set, &uc->uc_sigmask, sizeof(set))) |
diff --git a/arch/powerpc/kernel/syscalls.c b/arch/powerpc/kernel/syscalls.c index 466216506eb2..e6982ab21816 100644 --- a/arch/powerpc/kernel/syscalls.c +++ b/arch/powerpc/kernel/syscalls.c | |||
@@ -89,7 +89,7 @@ ppc_select(int n, fd_set __user *inp, fd_set __user *outp, fd_set __user *exp, s | |||
89 | if ( (unsigned long)n >= 4096 ) | 89 | if ( (unsigned long)n >= 4096 ) |
90 | { | 90 | { |
91 | unsigned long __user *buffer = (unsigned long __user *)n; | 91 | unsigned long __user *buffer = (unsigned long __user *)n; |
92 | if (!access_ok(VERIFY_READ, buffer, 5*sizeof(unsigned long)) | 92 | if (!access_ok(buffer, 5*sizeof(unsigned long)) |
93 | || __get_user(n, buffer) | 93 | || __get_user(n, buffer) |
94 | || __get_user(inp, ((fd_set __user * __user *)(buffer+1))) | 94 | || __get_user(inp, ((fd_set __user * __user *)(buffer+1))) |
95 | || __get_user(outp, ((fd_set __user * __user *)(buffer+2))) | 95 | || __get_user(outp, ((fd_set __user * __user *)(buffer+2))) |
diff --git a/arch/powerpc/kernel/traps.c b/arch/powerpc/kernel/traps.c index 00af2c4febf4..64936b60d521 100644 --- a/arch/powerpc/kernel/traps.c +++ b/arch/powerpc/kernel/traps.c | |||
@@ -837,7 +837,7 @@ static void p9_hmi_special_emu(struct pt_regs *regs) | |||
837 | addr = (__force const void __user *)ea; | 837 | addr = (__force const void __user *)ea; |
838 | 838 | ||
839 | /* Check it */ | 839 | /* Check it */ |
840 | if (!access_ok(VERIFY_READ, addr, 16)) { | 840 | if (!access_ok(addr, 16)) { |
841 | pr_devel("HMI vec emu: bad access %i:%s[%d] nip=%016lx" | 841 | pr_devel("HMI vec emu: bad access %i:%s[%d] nip=%016lx" |
842 | " instr=%08x addr=%016lx\n", | 842 | " instr=%08x addr=%016lx\n", |
843 | smp_processor_id(), current->comm, current->pid, | 843 | smp_processor_id(), current->comm, current->pid, |
diff --git a/arch/powerpc/kvm/book3s_64_mmu_hv.c b/arch/powerpc/kvm/book3s_64_mmu_hv.c index 6f2d2fb4e098..bd2dcfbf00cd 100644 --- a/arch/powerpc/kvm/book3s_64_mmu_hv.c +++ b/arch/powerpc/kvm/book3s_64_mmu_hv.c | |||
@@ -1744,7 +1744,7 @@ static ssize_t kvm_htab_read(struct file *file, char __user *buf, | |||
1744 | int first_pass; | 1744 | int first_pass; |
1745 | unsigned long hpte[2]; | 1745 | unsigned long hpte[2]; |
1746 | 1746 | ||
1747 | if (!access_ok(VERIFY_WRITE, buf, count)) | 1747 | if (!access_ok(buf, count)) |
1748 | return -EFAULT; | 1748 | return -EFAULT; |
1749 | if (kvm_is_radix(kvm)) | 1749 | if (kvm_is_radix(kvm)) |
1750 | return 0; | 1750 | return 0; |
@@ -1844,7 +1844,7 @@ static ssize_t kvm_htab_write(struct file *file, const char __user *buf, | |||
1844 | int mmu_ready; | 1844 | int mmu_ready; |
1845 | int pshift; | 1845 | int pshift; |
1846 | 1846 | ||
1847 | if (!access_ok(VERIFY_READ, buf, count)) | 1847 | if (!access_ok(buf, count)) |
1848 | return -EFAULT; | 1848 | return -EFAULT; |
1849 | if (kvm_is_radix(kvm)) | 1849 | if (kvm_is_radix(kvm)) |
1850 | return -EINVAL; | 1850 | return -EINVAL; |
diff --git a/arch/powerpc/lib/checksum_wrappers.c b/arch/powerpc/lib/checksum_wrappers.c index a0cb63fb76a1..890d4ddd91d6 100644 --- a/arch/powerpc/lib/checksum_wrappers.c +++ b/arch/powerpc/lib/checksum_wrappers.c | |||
@@ -37,7 +37,7 @@ __wsum csum_and_copy_from_user(const void __user *src, void *dst, | |||
37 | goto out; | 37 | goto out; |
38 | } | 38 | } |
39 | 39 | ||
40 | if (unlikely((len < 0) || !access_ok(VERIFY_READ, src, len))) { | 40 | if (unlikely((len < 0) || !access_ok(src, len))) { |
41 | *err_ptr = -EFAULT; | 41 | *err_ptr = -EFAULT; |
42 | csum = (__force unsigned int)sum; | 42 | csum = (__force unsigned int)sum; |
43 | goto out; | 43 | goto out; |
@@ -78,7 +78,7 @@ __wsum csum_and_copy_to_user(const void *src, void __user *dst, int len, | |||
78 | goto out; | 78 | goto out; |
79 | } | 79 | } |
80 | 80 | ||
81 | if (unlikely((len < 0) || !access_ok(VERIFY_WRITE, dst, len))) { | 81 | if (unlikely((len < 0) || !access_ok(dst, len))) { |
82 | *err_ptr = -EFAULT; | 82 | *err_ptr = -EFAULT; |
83 | csum = -1; /* invalid checksum */ | 83 | csum = -1; /* invalid checksum */ |
84 | goto out; | 84 | goto out; |
diff --git a/arch/powerpc/mm/fault.c b/arch/powerpc/mm/fault.c index a6dcfda3e11e..887f11bcf330 100644 --- a/arch/powerpc/mm/fault.c +++ b/arch/powerpc/mm/fault.c | |||
@@ -274,7 +274,7 @@ static bool bad_stack_expansion(struct pt_regs *regs, unsigned long address, | |||
274 | return false; | 274 | return false; |
275 | 275 | ||
276 | if ((flags & FAULT_FLAG_WRITE) && (flags & FAULT_FLAG_USER) && | 276 | if ((flags & FAULT_FLAG_WRITE) && (flags & FAULT_FLAG_USER) && |
277 | access_ok(VERIFY_READ, nip, sizeof(*nip))) { | 277 | access_ok(nip, sizeof(*nip))) { |
278 | unsigned int inst; | 278 | unsigned int inst; |
279 | int res; | 279 | int res; |
280 | 280 | ||
diff --git a/arch/powerpc/mm/subpage-prot.c b/arch/powerpc/mm/subpage-prot.c index 3327551c8b47..5e4178790dee 100644 --- a/arch/powerpc/mm/subpage-prot.c +++ b/arch/powerpc/mm/subpage-prot.c | |||
@@ -214,7 +214,7 @@ SYSCALL_DEFINE3(subpage_prot, unsigned long, addr, | |||
214 | return 0; | 214 | return 0; |
215 | } | 215 | } |
216 | 216 | ||
217 | if (!access_ok(VERIFY_READ, map, (len >> PAGE_SHIFT) * sizeof(u32))) | 217 | if (!access_ok(map, (len >> PAGE_SHIFT) * sizeof(u32))) |
218 | return -EFAULT; | 218 | return -EFAULT; |
219 | 219 | ||
220 | down_write(&mm->mmap_sem); | 220 | down_write(&mm->mmap_sem); |
diff --git a/arch/powerpc/oprofile/backtrace.c b/arch/powerpc/oprofile/backtrace.c index 5df6290d1ccc..260c53700978 100644 --- a/arch/powerpc/oprofile/backtrace.c +++ b/arch/powerpc/oprofile/backtrace.c | |||
@@ -31,7 +31,7 @@ static unsigned int user_getsp32(unsigned int sp, int is_first) | |||
31 | unsigned int stack_frame[2]; | 31 | unsigned int stack_frame[2]; |
32 | void __user *p = compat_ptr(sp); | 32 | void __user *p = compat_ptr(sp); |
33 | 33 | ||
34 | if (!access_ok(VERIFY_READ, p, sizeof(stack_frame))) | 34 | if (!access_ok(p, sizeof(stack_frame))) |
35 | return 0; | 35 | return 0; |
36 | 36 | ||
37 | /* | 37 | /* |
@@ -57,7 +57,7 @@ static unsigned long user_getsp64(unsigned long sp, int is_first) | |||
57 | { | 57 | { |
58 | unsigned long stack_frame[3]; | 58 | unsigned long stack_frame[3]; |
59 | 59 | ||
60 | if (!access_ok(VERIFY_READ, (void __user *)sp, sizeof(stack_frame))) | 60 | if (!access_ok((void __user *)sp, sizeof(stack_frame))) |
61 | return 0; | 61 | return 0; |
62 | 62 | ||
63 | if (__copy_from_user_inatomic(stack_frame, (void __user *)sp, | 63 | if (__copy_from_user_inatomic(stack_frame, (void __user *)sp, |
diff --git a/arch/powerpc/platforms/cell/spufs/file.c b/arch/powerpc/platforms/cell/spufs/file.c index 43e7b93f27c7..ae8123edddc6 100644 --- a/arch/powerpc/platforms/cell/spufs/file.c +++ b/arch/powerpc/platforms/cell/spufs/file.c | |||
@@ -609,7 +609,7 @@ static ssize_t spufs_mbox_read(struct file *file, char __user *buf, | |||
609 | if (len < 4) | 609 | if (len < 4) |
610 | return -EINVAL; | 610 | return -EINVAL; |
611 | 611 | ||
612 | if (!access_ok(VERIFY_WRITE, buf, len)) | 612 | if (!access_ok(buf, len)) |
613 | return -EFAULT; | 613 | return -EFAULT; |
614 | 614 | ||
615 | udata = (void __user *)buf; | 615 | udata = (void __user *)buf; |
@@ -717,7 +717,7 @@ static ssize_t spufs_ibox_read(struct file *file, char __user *buf, | |||
717 | if (len < 4) | 717 | if (len < 4) |
718 | return -EINVAL; | 718 | return -EINVAL; |
719 | 719 | ||
720 | if (!access_ok(VERIFY_WRITE, buf, len)) | 720 | if (!access_ok(buf, len)) |
721 | return -EFAULT; | 721 | return -EFAULT; |
722 | 722 | ||
723 | udata = (void __user *)buf; | 723 | udata = (void __user *)buf; |
@@ -856,7 +856,7 @@ static ssize_t spufs_wbox_write(struct file *file, const char __user *buf, | |||
856 | return -EINVAL; | 856 | return -EINVAL; |
857 | 857 | ||
858 | udata = (void __user *)buf; | 858 | udata = (void __user *)buf; |
859 | if (!access_ok(VERIFY_READ, buf, len)) | 859 | if (!access_ok(buf, len)) |
860 | return -EFAULT; | 860 | return -EFAULT; |
861 | 861 | ||
862 | if (__get_user(wbox_data, udata)) | 862 | if (__get_user(wbox_data, udata)) |
@@ -1994,7 +1994,7 @@ static ssize_t spufs_mbox_info_read(struct file *file, char __user *buf, | |||
1994 | int ret; | 1994 | int ret; |
1995 | struct spu_context *ctx = file->private_data; | 1995 | struct spu_context *ctx = file->private_data; |
1996 | 1996 | ||
1997 | if (!access_ok(VERIFY_WRITE, buf, len)) | 1997 | if (!access_ok(buf, len)) |
1998 | return -EFAULT; | 1998 | return -EFAULT; |
1999 | 1999 | ||
2000 | ret = spu_acquire_saved(ctx); | 2000 | ret = spu_acquire_saved(ctx); |
@@ -2034,7 +2034,7 @@ static ssize_t spufs_ibox_info_read(struct file *file, char __user *buf, | |||
2034 | struct spu_context *ctx = file->private_data; | 2034 | struct spu_context *ctx = file->private_data; |
2035 | int ret; | 2035 | int ret; |
2036 | 2036 | ||
2037 | if (!access_ok(VERIFY_WRITE, buf, len)) | 2037 | if (!access_ok(buf, len)) |
2038 | return -EFAULT; | 2038 | return -EFAULT; |
2039 | 2039 | ||
2040 | ret = spu_acquire_saved(ctx); | 2040 | ret = spu_acquire_saved(ctx); |
@@ -2077,7 +2077,7 @@ static ssize_t spufs_wbox_info_read(struct file *file, char __user *buf, | |||
2077 | struct spu_context *ctx = file->private_data; | 2077 | struct spu_context *ctx = file->private_data; |
2078 | int ret; | 2078 | int ret; |
2079 | 2079 | ||
2080 | if (!access_ok(VERIFY_WRITE, buf, len)) | 2080 | if (!access_ok(buf, len)) |
2081 | return -EFAULT; | 2081 | return -EFAULT; |
2082 | 2082 | ||
2083 | ret = spu_acquire_saved(ctx); | 2083 | ret = spu_acquire_saved(ctx); |
@@ -2129,7 +2129,7 @@ static ssize_t spufs_dma_info_read(struct file *file, char __user *buf, | |||
2129 | struct spu_context *ctx = file->private_data; | 2129 | struct spu_context *ctx = file->private_data; |
2130 | int ret; | 2130 | int ret; |
2131 | 2131 | ||
2132 | if (!access_ok(VERIFY_WRITE, buf, len)) | 2132 | if (!access_ok(buf, len)) |
2133 | return -EFAULT; | 2133 | return -EFAULT; |
2134 | 2134 | ||
2135 | ret = spu_acquire_saved(ctx); | 2135 | ret = spu_acquire_saved(ctx); |
@@ -2160,7 +2160,7 @@ static ssize_t __spufs_proxydma_info_read(struct spu_context *ctx, | |||
2160 | if (len < ret) | 2160 | if (len < ret) |
2161 | return -EINVAL; | 2161 | return -EINVAL; |
2162 | 2162 | ||
2163 | if (!access_ok(VERIFY_WRITE, buf, len)) | 2163 | if (!access_ok(buf, len)) |
2164 | return -EFAULT; | 2164 | return -EFAULT; |
2165 | 2165 | ||
2166 | info.proxydma_info_type = ctx->csa.prob.dma_querytype_RW; | 2166 | info.proxydma_info_type = ctx->csa.prob.dma_querytype_RW; |
diff --git a/arch/powerpc/platforms/powernv/opal-lpc.c b/arch/powerpc/platforms/powernv/opal-lpc.c index 6c7ad1d8b32e..2623996a193a 100644 --- a/arch/powerpc/platforms/powernv/opal-lpc.c +++ b/arch/powerpc/platforms/powernv/opal-lpc.c | |||
@@ -192,7 +192,7 @@ static ssize_t lpc_debug_read(struct file *filp, char __user *ubuf, | |||
192 | u32 data, pos, len, todo; | 192 | u32 data, pos, len, todo; |
193 | int rc; | 193 | int rc; |
194 | 194 | ||
195 | if (!access_ok(VERIFY_WRITE, ubuf, count)) | 195 | if (!access_ok(ubuf, count)) |
196 | return -EFAULT; | 196 | return -EFAULT; |
197 | 197 | ||
198 | todo = count; | 198 | todo = count; |
@@ -283,7 +283,7 @@ static ssize_t lpc_debug_write(struct file *filp, const char __user *ubuf, | |||
283 | u32 data, pos, len, todo; | 283 | u32 data, pos, len, todo; |
284 | int rc; | 284 | int rc; |
285 | 285 | ||
286 | if (!access_ok(VERIFY_READ, ubuf, count)) | 286 | if (!access_ok(ubuf, count)) |
287 | return -EFAULT; | 287 | return -EFAULT; |
288 | 288 | ||
289 | todo = count; | 289 | todo = count; |
diff --git a/arch/powerpc/platforms/pseries/scanlog.c b/arch/powerpc/platforms/pseries/scanlog.c index 054ce7a16fc3..24b157e1e890 100644 --- a/arch/powerpc/platforms/pseries/scanlog.c +++ b/arch/powerpc/platforms/pseries/scanlog.c | |||
@@ -63,7 +63,7 @@ static ssize_t scanlog_read(struct file *file, char __user *buf, | |||
63 | return -EINVAL; | 63 | return -EINVAL; |
64 | } | 64 | } |
65 | 65 | ||
66 | if (!access_ok(VERIFY_WRITE, buf, count)) | 66 | if (!access_ok(buf, count)) |
67 | return -EFAULT; | 67 | return -EFAULT; |
68 | 68 | ||
69 | for (;;) { | 69 | for (;;) { |
diff --git a/arch/riscv/include/asm/futex.h b/arch/riscv/include/asm/futex.h index 3b19eba1bc8e..66641624d8a5 100644 --- a/arch/riscv/include/asm/futex.h +++ b/arch/riscv/include/asm/futex.h | |||
@@ -95,7 +95,7 @@ futex_atomic_cmpxchg_inatomic(u32 *uval, u32 __user *uaddr, | |||
95 | u32 val; | 95 | u32 val; |
96 | uintptr_t tmp; | 96 | uintptr_t tmp; |
97 | 97 | ||
98 | if (!access_ok(VERIFY_WRITE, uaddr, sizeof(u32))) | 98 | if (!access_ok(uaddr, sizeof(u32))) |
99 | return -EFAULT; | 99 | return -EFAULT; |
100 | 100 | ||
101 | __enable_user_access(); | 101 | __enable_user_access(); |
diff --git a/arch/riscv/include/asm/uaccess.h b/arch/riscv/include/asm/uaccess.h index 8c3e3e3c8be1..637b896894fc 100644 --- a/arch/riscv/include/asm/uaccess.h +++ b/arch/riscv/include/asm/uaccess.h | |||
@@ -54,14 +54,8 @@ static inline void set_fs(mm_segment_t fs) | |||
54 | #define user_addr_max() (get_fs()) | 54 | #define user_addr_max() (get_fs()) |
55 | 55 | ||
56 | 56 | ||
57 | #define VERIFY_READ 0 | ||
58 | #define VERIFY_WRITE 1 | ||
59 | |||
60 | /** | 57 | /** |
61 | * access_ok: - Checks if a user space pointer is valid | 58 | * access_ok: - Checks if a user space pointer is valid |
62 | * @type: Type of access: %VERIFY_READ or %VERIFY_WRITE. Note that | ||
63 | * %VERIFY_WRITE is a superset of %VERIFY_READ - if it is safe | ||
64 | * to write to a block, it is always safe to read from it. | ||
65 | * @addr: User space pointer to start of block to check | 59 | * @addr: User space pointer to start of block to check |
66 | * @size: Size of block to check | 60 | * @size: Size of block to check |
67 | * | 61 | * |
@@ -76,7 +70,7 @@ static inline void set_fs(mm_segment_t fs) | |||
76 | * checks that the pointer is in the user space range - after calling | 70 | * checks that the pointer is in the user space range - after calling |
77 | * this function, memory access functions may still return -EFAULT. | 71 | * this function, memory access functions may still return -EFAULT. |
78 | */ | 72 | */ |
79 | #define access_ok(type, addr, size) ({ \ | 73 | #define access_ok(addr, size) ({ \ |
80 | __chk_user_ptr(addr); \ | 74 | __chk_user_ptr(addr); \ |
81 | likely(__access_ok((unsigned long __force)(addr), (size))); \ | 75 | likely(__access_ok((unsigned long __force)(addr), (size))); \ |
82 | }) | 76 | }) |
@@ -258,7 +252,7 @@ do { \ | |||
258 | ({ \ | 252 | ({ \ |
259 | const __typeof__(*(ptr)) __user *__p = (ptr); \ | 253 | const __typeof__(*(ptr)) __user *__p = (ptr); \ |
260 | might_fault(); \ | 254 | might_fault(); \ |
261 | access_ok(VERIFY_READ, __p, sizeof(*__p)) ? \ | 255 | access_ok(__p, sizeof(*__p)) ? \ |
262 | __get_user((x), __p) : \ | 256 | __get_user((x), __p) : \ |
263 | ((x) = 0, -EFAULT); \ | 257 | ((x) = 0, -EFAULT); \ |
264 | }) | 258 | }) |
@@ -386,7 +380,7 @@ do { \ | |||
386 | ({ \ | 380 | ({ \ |
387 | __typeof__(*(ptr)) __user *__p = (ptr); \ | 381 | __typeof__(*(ptr)) __user *__p = (ptr); \ |
388 | might_fault(); \ | 382 | might_fault(); \ |
389 | access_ok(VERIFY_WRITE, __p, sizeof(*__p)) ? \ | 383 | access_ok(__p, sizeof(*__p)) ? \ |
390 | __put_user((x), __p) : \ | 384 | __put_user((x), __p) : \ |
391 | -EFAULT; \ | 385 | -EFAULT; \ |
392 | }) | 386 | }) |
@@ -421,7 +415,7 @@ static inline | |||
421 | unsigned long __must_check clear_user(void __user *to, unsigned long n) | 415 | unsigned long __must_check clear_user(void __user *to, unsigned long n) |
422 | { | 416 | { |
423 | might_fault(); | 417 | might_fault(); |
424 | return access_ok(VERIFY_WRITE, to, n) ? | 418 | return access_ok(to, n) ? |
425 | __clear_user(to, n) : n; | 419 | __clear_user(to, n) : n; |
426 | } | 420 | } |
427 | 421 | ||
diff --git a/arch/riscv/kernel/signal.c b/arch/riscv/kernel/signal.c index f9b5e7e352ef..837e1646091a 100644 --- a/arch/riscv/kernel/signal.c +++ b/arch/riscv/kernel/signal.c | |||
@@ -115,7 +115,7 @@ SYSCALL_DEFINE0(rt_sigreturn) | |||
115 | 115 | ||
116 | frame = (struct rt_sigframe __user *)regs->sp; | 116 | frame = (struct rt_sigframe __user *)regs->sp; |
117 | 117 | ||
118 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 118 | if (!access_ok(frame, sizeof(*frame))) |
119 | goto badframe; | 119 | goto badframe; |
120 | 120 | ||
121 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) | 121 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) |
@@ -187,7 +187,7 @@ static int setup_rt_frame(struct ksignal *ksig, sigset_t *set, | |||
187 | long err = 0; | 187 | long err = 0; |
188 | 188 | ||
189 | frame = get_sigframe(ksig, regs, sizeof(*frame)); | 189 | frame = get_sigframe(ksig, regs, sizeof(*frame)); |
190 | if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame))) | 190 | if (!access_ok(frame, sizeof(*frame))) |
191 | return -EFAULT; | 191 | return -EFAULT; |
192 | 192 | ||
193 | err |= copy_siginfo_to_user(&frame->info, &ksig->info); | 193 | err |= copy_siginfo_to_user(&frame->info, &ksig->info); |
diff --git a/arch/s390/include/asm/uaccess.h b/arch/s390/include/asm/uaccess.h index ad6b91013a05..bd2545977ad3 100644 --- a/arch/s390/include/asm/uaccess.h +++ b/arch/s390/include/asm/uaccess.h | |||
@@ -48,7 +48,7 @@ static inline int __range_ok(unsigned long addr, unsigned long size) | |||
48 | __range_ok((unsigned long)(addr), (size)); \ | 48 | __range_ok((unsigned long)(addr), (size)); \ |
49 | }) | 49 | }) |
50 | 50 | ||
51 | #define access_ok(type, addr, size) __access_ok(addr, size) | 51 | #define access_ok(addr, size) __access_ok(addr, size) |
52 | 52 | ||
53 | unsigned long __must_check | 53 | unsigned long __must_check |
54 | raw_copy_from_user(void *to, const void __user *from, unsigned long n); | 54 | raw_copy_from_user(void *to, const void __user *from, unsigned long n); |
diff --git a/arch/sh/include/asm/checksum_32.h b/arch/sh/include/asm/checksum_32.h index b58f3d95dc19..36b84cfd3f67 100644 --- a/arch/sh/include/asm/checksum_32.h +++ b/arch/sh/include/asm/checksum_32.h | |||
@@ -197,7 +197,7 @@ static inline __wsum csum_and_copy_to_user(const void *src, | |||
197 | int len, __wsum sum, | 197 | int len, __wsum sum, |
198 | int *err_ptr) | 198 | int *err_ptr) |
199 | { | 199 | { |
200 | if (access_ok(VERIFY_WRITE, dst, len)) | 200 | if (access_ok(dst, len)) |
201 | return csum_partial_copy_generic((__force const void *)src, | 201 | return csum_partial_copy_generic((__force const void *)src, |
202 | dst, len, sum, NULL, err_ptr); | 202 | dst, len, sum, NULL, err_ptr); |
203 | 203 | ||
diff --git a/arch/sh/include/asm/futex.h b/arch/sh/include/asm/futex.h index 6d192f4908a7..3190ec89df81 100644 --- a/arch/sh/include/asm/futex.h +++ b/arch/sh/include/asm/futex.h | |||
@@ -22,7 +22,7 @@ static inline int | |||
22 | futex_atomic_cmpxchg_inatomic(u32 *uval, u32 __user *uaddr, | 22 | futex_atomic_cmpxchg_inatomic(u32 *uval, u32 __user *uaddr, |
23 | u32 oldval, u32 newval) | 23 | u32 oldval, u32 newval) |
24 | { | 24 | { |
25 | if (!access_ok(VERIFY_WRITE, uaddr, sizeof(u32))) | 25 | if (!access_ok(uaddr, sizeof(u32))) |
26 | return -EFAULT; | 26 | return -EFAULT; |
27 | 27 | ||
28 | return atomic_futex_op_cmpxchg_inatomic(uval, uaddr, oldval, newval); | 28 | return atomic_futex_op_cmpxchg_inatomic(uval, uaddr, oldval, newval); |
diff --git a/arch/sh/include/asm/uaccess.h b/arch/sh/include/asm/uaccess.h index 32eb56e00c11..deebbfab5342 100644 --- a/arch/sh/include/asm/uaccess.h +++ b/arch/sh/include/asm/uaccess.h | |||
@@ -18,7 +18,7 @@ | |||
18 | */ | 18 | */ |
19 | #define __access_ok(addr, size) \ | 19 | #define __access_ok(addr, size) \ |
20 | (__addr_ok((addr) + (size))) | 20 | (__addr_ok((addr) + (size))) |
21 | #define access_ok(type, addr, size) \ | 21 | #define access_ok(addr, size) \ |
22 | (__chk_user_ptr(addr), \ | 22 | (__chk_user_ptr(addr), \ |
23 | __access_ok((unsigned long __force)(addr), (size))) | 23 | __access_ok((unsigned long __force)(addr), (size))) |
24 | 24 | ||
@@ -66,7 +66,7 @@ struct __large_struct { unsigned long buf[100]; }; | |||
66 | long __gu_err = -EFAULT; \ | 66 | long __gu_err = -EFAULT; \ |
67 | unsigned long __gu_val = 0; \ | 67 | unsigned long __gu_val = 0; \ |
68 | const __typeof__(*(ptr)) *__gu_addr = (ptr); \ | 68 | const __typeof__(*(ptr)) *__gu_addr = (ptr); \ |
69 | if (likely(access_ok(VERIFY_READ, __gu_addr, (size)))) \ | 69 | if (likely(access_ok(__gu_addr, (size)))) \ |
70 | __get_user_size(__gu_val, __gu_addr, (size), __gu_err); \ | 70 | __get_user_size(__gu_val, __gu_addr, (size), __gu_err); \ |
71 | (x) = (__force __typeof__(*(ptr)))__gu_val; \ | 71 | (x) = (__force __typeof__(*(ptr)))__gu_val; \ |
72 | __gu_err; \ | 72 | __gu_err; \ |
@@ -87,7 +87,7 @@ struct __large_struct { unsigned long buf[100]; }; | |||
87 | long __pu_err = -EFAULT; \ | 87 | long __pu_err = -EFAULT; \ |
88 | __typeof__(*(ptr)) __user *__pu_addr = (ptr); \ | 88 | __typeof__(*(ptr)) __user *__pu_addr = (ptr); \ |
89 | __typeof__(*(ptr)) __pu_val = x; \ | 89 | __typeof__(*(ptr)) __pu_val = x; \ |
90 | if (likely(access_ok(VERIFY_WRITE, __pu_addr, size))) \ | 90 | if (likely(access_ok(__pu_addr, size))) \ |
91 | __put_user_size(__pu_val, __pu_addr, (size), \ | 91 | __put_user_size(__pu_val, __pu_addr, (size), \ |
92 | __pu_err); \ | 92 | __pu_err); \ |
93 | __pu_err; \ | 93 | __pu_err; \ |
@@ -132,8 +132,7 @@ __kernel_size_t __clear_user(void *addr, __kernel_size_t size); | |||
132 | void __user * __cl_addr = (addr); \ | 132 | void __user * __cl_addr = (addr); \ |
133 | unsigned long __cl_size = (n); \ | 133 | unsigned long __cl_size = (n); \ |
134 | \ | 134 | \ |
135 | if (__cl_size && access_ok(VERIFY_WRITE, \ | 135 | if (__cl_size && access_ok(__cl_addr, __cl_size)) \ |
136 | ((unsigned long)(__cl_addr)), __cl_size)) \ | ||
137 | __cl_size = __clear_user(__cl_addr, __cl_size); \ | 136 | __cl_size = __clear_user(__cl_addr, __cl_size); \ |
138 | \ | 137 | \ |
139 | __cl_size; \ | 138 | __cl_size; \ |
diff --git a/arch/sh/kernel/signal_32.c b/arch/sh/kernel/signal_32.c index c46c0020ff55..2a2121ba8ebe 100644 --- a/arch/sh/kernel/signal_32.c +++ b/arch/sh/kernel/signal_32.c | |||
@@ -160,7 +160,7 @@ asmlinkage int sys_sigreturn(void) | |||
160 | /* Always make any pending restarted system calls return -EINTR */ | 160 | /* Always make any pending restarted system calls return -EINTR */ |
161 | current->restart_block.fn = do_no_restart_syscall; | 161 | current->restart_block.fn = do_no_restart_syscall; |
162 | 162 | ||
163 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 163 | if (!access_ok(frame, sizeof(*frame))) |
164 | goto badframe; | 164 | goto badframe; |
165 | 165 | ||
166 | if (__get_user(set.sig[0], &frame->sc.oldmask) | 166 | if (__get_user(set.sig[0], &frame->sc.oldmask) |
@@ -190,7 +190,7 @@ asmlinkage int sys_rt_sigreturn(void) | |||
190 | /* Always make any pending restarted system calls return -EINTR */ | 190 | /* Always make any pending restarted system calls return -EINTR */ |
191 | current->restart_block.fn = do_no_restart_syscall; | 191 | current->restart_block.fn = do_no_restart_syscall; |
192 | 192 | ||
193 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 193 | if (!access_ok(frame, sizeof(*frame))) |
194 | goto badframe; | 194 | goto badframe; |
195 | 195 | ||
196 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) | 196 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) |
@@ -272,7 +272,7 @@ static int setup_frame(struct ksignal *ksig, sigset_t *set, | |||
272 | 272 | ||
273 | frame = get_sigframe(&ksig->ka, regs->regs[15], sizeof(*frame)); | 273 | frame = get_sigframe(&ksig->ka, regs->regs[15], sizeof(*frame)); |
274 | 274 | ||
275 | if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame))) | 275 | if (!access_ok(frame, sizeof(*frame))) |
276 | return -EFAULT; | 276 | return -EFAULT; |
277 | 277 | ||
278 | err |= setup_sigcontext(&frame->sc, regs, set->sig[0]); | 278 | err |= setup_sigcontext(&frame->sc, regs, set->sig[0]); |
@@ -338,7 +338,7 @@ static int setup_rt_frame(struct ksignal *ksig, sigset_t *set, | |||
338 | 338 | ||
339 | frame = get_sigframe(&ksig->ka, regs->regs[15], sizeof(*frame)); | 339 | frame = get_sigframe(&ksig->ka, regs->regs[15], sizeof(*frame)); |
340 | 340 | ||
341 | if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame))) | 341 | if (!access_ok(frame, sizeof(*frame))) |
342 | return -EFAULT; | 342 | return -EFAULT; |
343 | 343 | ||
344 | err |= copy_siginfo_to_user(&frame->info, &ksig->info); | 344 | err |= copy_siginfo_to_user(&frame->info, &ksig->info); |
diff --git a/arch/sh/kernel/signal_64.c b/arch/sh/kernel/signal_64.c index 76661dee3c65..f1f1598879c2 100644 --- a/arch/sh/kernel/signal_64.c +++ b/arch/sh/kernel/signal_64.c | |||
@@ -259,7 +259,7 @@ asmlinkage int sys_sigreturn(unsigned long r2, unsigned long r3, | |||
259 | /* Always make any pending restarted system calls return -EINTR */ | 259 | /* Always make any pending restarted system calls return -EINTR */ |
260 | current->restart_block.fn = do_no_restart_syscall; | 260 | current->restart_block.fn = do_no_restart_syscall; |
261 | 261 | ||
262 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 262 | if (!access_ok(frame, sizeof(*frame))) |
263 | goto badframe; | 263 | goto badframe; |
264 | 264 | ||
265 | if (__get_user(set.sig[0], &frame->sc.oldmask) | 265 | if (__get_user(set.sig[0], &frame->sc.oldmask) |
@@ -293,7 +293,7 @@ asmlinkage int sys_rt_sigreturn(unsigned long r2, unsigned long r3, | |||
293 | /* Always make any pending restarted system calls return -EINTR */ | 293 | /* Always make any pending restarted system calls return -EINTR */ |
294 | current->restart_block.fn = do_no_restart_syscall; | 294 | current->restart_block.fn = do_no_restart_syscall; |
295 | 295 | ||
296 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 296 | if (!access_ok(frame, sizeof(*frame))) |
297 | goto badframe; | 297 | goto badframe; |
298 | 298 | ||
299 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) | 299 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) |
@@ -379,7 +379,7 @@ static int setup_frame(struct ksignal *ksig, sigset_t *set, struct pt_regs *regs | |||
379 | 379 | ||
380 | frame = get_sigframe(&ksig->ka, regs->regs[REG_SP], sizeof(*frame)); | 380 | frame = get_sigframe(&ksig->ka, regs->regs[REG_SP], sizeof(*frame)); |
381 | 381 | ||
382 | if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame))) | 382 | if (!access_ok(frame, sizeof(*frame))) |
383 | return -EFAULT; | 383 | return -EFAULT; |
384 | 384 | ||
385 | err |= setup_sigcontext(&frame->sc, regs, set->sig[0]); | 385 | err |= setup_sigcontext(&frame->sc, regs, set->sig[0]); |
@@ -465,7 +465,7 @@ static int setup_rt_frame(struct ksignal *kig, sigset_t *set, | |||
465 | 465 | ||
466 | frame = get_sigframe(&ksig->ka, regs->regs[REG_SP], sizeof(*frame)); | 466 | frame = get_sigframe(&ksig->ka, regs->regs[REG_SP], sizeof(*frame)); |
467 | 467 | ||
468 | if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame))) | 468 | if (!access_ok(frame, sizeof(*frame))) |
469 | return -EFAULT; | 469 | return -EFAULT; |
470 | 470 | ||
471 | err |= __put_user(&frame->info, &frame->pinfo); | 471 | err |= __put_user(&frame->info, &frame->pinfo); |
diff --git a/arch/sh/kernel/traps_64.c b/arch/sh/kernel/traps_64.c index c52bda4d2574..8ce90a7da67d 100644 --- a/arch/sh/kernel/traps_64.c +++ b/arch/sh/kernel/traps_64.c | |||
@@ -40,7 +40,7 @@ static int read_opcode(reg_size_t pc, insn_size_t *result_opcode, int from_user_ | |||
40 | /* SHmedia */ | 40 | /* SHmedia */ |
41 | aligned_pc = pc & ~3; | 41 | aligned_pc = pc & ~3; |
42 | if (from_user_mode) { | 42 | if (from_user_mode) { |
43 | if (!access_ok(VERIFY_READ, aligned_pc, sizeof(insn_size_t))) { | 43 | if (!access_ok(aligned_pc, sizeof(insn_size_t))) { |
44 | get_user_error = -EFAULT; | 44 | get_user_error = -EFAULT; |
45 | } else { | 45 | } else { |
46 | get_user_error = __get_user(opcode, (insn_size_t *)aligned_pc); | 46 | get_user_error = __get_user(opcode, (insn_size_t *)aligned_pc); |
@@ -180,7 +180,7 @@ static int misaligned_load(struct pt_regs *regs, | |||
180 | if (user_mode(regs)) { | 180 | if (user_mode(regs)) { |
181 | __u64 buffer; | 181 | __u64 buffer; |
182 | 182 | ||
183 | if (!access_ok(VERIFY_READ, (unsigned long) address, 1UL<<width_shift)) { | 183 | if (!access_ok((unsigned long) address, 1UL<<width_shift)) { |
184 | return -1; | 184 | return -1; |
185 | } | 185 | } |
186 | 186 | ||
@@ -254,7 +254,7 @@ static int misaligned_store(struct pt_regs *regs, | |||
254 | if (user_mode(regs)) { | 254 | if (user_mode(regs)) { |
255 | __u64 buffer; | 255 | __u64 buffer; |
256 | 256 | ||
257 | if (!access_ok(VERIFY_WRITE, (unsigned long) address, 1UL<<width_shift)) { | 257 | if (!access_ok((unsigned long) address, 1UL<<width_shift)) { |
258 | return -1; | 258 | return -1; |
259 | } | 259 | } |
260 | 260 | ||
@@ -327,7 +327,7 @@ static int misaligned_fpu_load(struct pt_regs *regs, | |||
327 | __u64 buffer; | 327 | __u64 buffer; |
328 | __u32 buflo, bufhi; | 328 | __u32 buflo, bufhi; |
329 | 329 | ||
330 | if (!access_ok(VERIFY_READ, (unsigned long) address, 1UL<<width_shift)) { | 330 | if (!access_ok((unsigned long) address, 1UL<<width_shift)) { |
331 | return -1; | 331 | return -1; |
332 | } | 332 | } |
333 | 333 | ||
@@ -400,7 +400,7 @@ static int misaligned_fpu_store(struct pt_regs *regs, | |||
400 | /* Initialise these to NaNs. */ | 400 | /* Initialise these to NaNs. */ |
401 | __u32 buflo=0xffffffffUL, bufhi=0xffffffffUL; | 401 | __u32 buflo=0xffffffffUL, bufhi=0xffffffffUL; |
402 | 402 | ||
403 | if (!access_ok(VERIFY_WRITE, (unsigned long) address, 1UL<<width_shift)) { | 403 | if (!access_ok((unsigned long) address, 1UL<<width_shift)) { |
404 | return -1; | 404 | return -1; |
405 | } | 405 | } |
406 | 406 | ||
@@ -663,7 +663,7 @@ void do_reserved_inst(unsigned long error_code, struct pt_regs *regs) | |||
663 | /* SHmedia : check for defect. This requires executable vmas | 663 | /* SHmedia : check for defect. This requires executable vmas |
664 | to be readable too. */ | 664 | to be readable too. */ |
665 | aligned_pc = pc & ~3; | 665 | aligned_pc = pc & ~3; |
666 | if (!access_ok(VERIFY_READ, aligned_pc, sizeof(insn_size_t))) | 666 | if (!access_ok(aligned_pc, sizeof(insn_size_t))) |
667 | get_user_error = -EFAULT; | 667 | get_user_error = -EFAULT; |
668 | else | 668 | else |
669 | get_user_error = __get_user(opcode, (insn_size_t *)aligned_pc); | 669 | get_user_error = __get_user(opcode, (insn_size_t *)aligned_pc); |
diff --git a/arch/sh/mm/gup.c b/arch/sh/mm/gup.c index 56c86ca98ecf..3e27f6d1f1ec 100644 --- a/arch/sh/mm/gup.c +++ b/arch/sh/mm/gup.c | |||
@@ -177,8 +177,7 @@ int __get_user_pages_fast(unsigned long start, int nr_pages, int write, | |||
177 | addr = start; | 177 | addr = start; |
178 | len = (unsigned long) nr_pages << PAGE_SHIFT; | 178 | len = (unsigned long) nr_pages << PAGE_SHIFT; |
179 | end = start + len; | 179 | end = start + len; |
180 | if (unlikely(!access_ok(write ? VERIFY_WRITE : VERIFY_READ, | 180 | if (unlikely(!access_ok((void __user *)start, len))) |
181 | (void __user *)start, len))) | ||
182 | return 0; | 181 | return 0; |
183 | 182 | ||
184 | /* | 183 | /* |
diff --git a/arch/sh/oprofile/backtrace.c b/arch/sh/oprofile/backtrace.c index c7695f99c8c3..8279a7e91043 100644 --- a/arch/sh/oprofile/backtrace.c +++ b/arch/sh/oprofile/backtrace.c | |||
@@ -51,7 +51,7 @@ user_backtrace(unsigned long *stackaddr, struct pt_regs *regs) | |||
51 | unsigned long buf_stack; | 51 | unsigned long buf_stack; |
52 | 52 | ||
53 | /* Also check accessibility of address */ | 53 | /* Also check accessibility of address */ |
54 | if (!access_ok(VERIFY_READ, stackaddr, sizeof(unsigned long))) | 54 | if (!access_ok(stackaddr, sizeof(unsigned long))) |
55 | return NULL; | 55 | return NULL; |
56 | 56 | ||
57 | if (__copy_from_user_inatomic(&buf_stack, stackaddr, sizeof(unsigned long))) | 57 | if (__copy_from_user_inatomic(&buf_stack, stackaddr, sizeof(unsigned long))) |
diff --git a/arch/sparc/include/asm/checksum_32.h b/arch/sparc/include/asm/checksum_32.h index d1e53d7aed39..5fc98d80b03b 100644 --- a/arch/sparc/include/asm/checksum_32.h +++ b/arch/sparc/include/asm/checksum_32.h | |||
@@ -87,7 +87,7 @@ static inline __wsum | |||
87 | csum_partial_copy_to_user(const void *src, void __user *dst, int len, | 87 | csum_partial_copy_to_user(const void *src, void __user *dst, int len, |
88 | __wsum sum, int *err) | 88 | __wsum sum, int *err) |
89 | { | 89 | { |
90 | if (!access_ok (VERIFY_WRITE, dst, len)) { | 90 | if (!access_ok(dst, len)) { |
91 | *err = -EFAULT; | 91 | *err = -EFAULT; |
92 | return sum; | 92 | return sum; |
93 | } else { | 93 | } else { |
diff --git a/arch/sparc/include/asm/uaccess_32.h b/arch/sparc/include/asm/uaccess_32.h index de71c65b99f0..5153798051fb 100644 --- a/arch/sparc/include/asm/uaccess_32.h +++ b/arch/sparc/include/asm/uaccess_32.h | |||
@@ -39,8 +39,7 @@ | |||
39 | #define __user_ok(addr, size) ({ (void)(size); (addr) < STACK_TOP; }) | 39 | #define __user_ok(addr, size) ({ (void)(size); (addr) < STACK_TOP; }) |
40 | #define __kernel_ok (uaccess_kernel()) | 40 | #define __kernel_ok (uaccess_kernel()) |
41 | #define __access_ok(addr, size) (__user_ok((addr) & get_fs().seg, (size))) | 41 | #define __access_ok(addr, size) (__user_ok((addr) & get_fs().seg, (size))) |
42 | #define access_ok(type, addr, size) \ | 42 | #define access_ok(addr, size) __access_ok((unsigned long)(addr), size) |
43 | ({ (void)(type); __access_ok((unsigned long)(addr), size); }) | ||
44 | 43 | ||
45 | /* | 44 | /* |
46 | * The exception table consists of pairs of addresses: the first is the | 45 | * The exception table consists of pairs of addresses: the first is the |
diff --git a/arch/sparc/include/asm/uaccess_64.h b/arch/sparc/include/asm/uaccess_64.h index cbb308cee394..87ae9ffb1521 100644 --- a/arch/sparc/include/asm/uaccess_64.h +++ b/arch/sparc/include/asm/uaccess_64.h | |||
@@ -68,7 +68,7 @@ static inline int __access_ok(const void __user * addr, unsigned long size) | |||
68 | return 1; | 68 | return 1; |
69 | } | 69 | } |
70 | 70 | ||
71 | static inline int access_ok(int type, const void __user * addr, unsigned long size) | 71 | static inline int access_ok(const void __user * addr, unsigned long size) |
72 | { | 72 | { |
73 | return 1; | 73 | return 1; |
74 | } | 74 | } |
diff --git a/arch/sparc/kernel/sigutil_32.c b/arch/sparc/kernel/sigutil_32.c index 1e9fae56a853..f25c6daa9f52 100644 --- a/arch/sparc/kernel/sigutil_32.c +++ b/arch/sparc/kernel/sigutil_32.c | |||
@@ -65,7 +65,7 @@ int restore_fpu_state(struct pt_regs *regs, __siginfo_fpu_t __user *fpu) | |||
65 | set_used_math(); | 65 | set_used_math(); |
66 | clear_tsk_thread_flag(current, TIF_USEDFPU); | 66 | clear_tsk_thread_flag(current, TIF_USEDFPU); |
67 | 67 | ||
68 | if (!access_ok(VERIFY_READ, fpu, sizeof(*fpu))) | 68 | if (!access_ok(fpu, sizeof(*fpu))) |
69 | return -EFAULT; | 69 | return -EFAULT; |
70 | 70 | ||
71 | err = __copy_from_user(¤t->thread.float_regs[0], &fpu->si_float_regs[0], | 71 | err = __copy_from_user(¤t->thread.float_regs[0], &fpu->si_float_regs[0], |
diff --git a/arch/sparc/kernel/unaligned_32.c b/arch/sparc/kernel/unaligned_32.c index 64ac8c0c1429..83db94c0b431 100644 --- a/arch/sparc/kernel/unaligned_32.c +++ b/arch/sparc/kernel/unaligned_32.c | |||
@@ -278,7 +278,6 @@ static inline int ok_for_user(struct pt_regs *regs, unsigned int insn, | |||
278 | enum direction dir) | 278 | enum direction dir) |
279 | { | 279 | { |
280 | unsigned int reg; | 280 | unsigned int reg; |
281 | int check = (dir == load) ? VERIFY_READ : VERIFY_WRITE; | ||
282 | int size = ((insn >> 19) & 3) == 3 ? 8 : 4; | 281 | int size = ((insn >> 19) & 3) == 3 ? 8 : 4; |
283 | 282 | ||
284 | if ((regs->pc | regs->npc) & 3) | 283 | if ((regs->pc | regs->npc) & 3) |
@@ -290,18 +289,18 @@ static inline int ok_for_user(struct pt_regs *regs, unsigned int insn, | |||
290 | 289 | ||
291 | reg = (insn >> 25) & 0x1f; | 290 | reg = (insn >> 25) & 0x1f; |
292 | if (reg >= 16) { | 291 | if (reg >= 16) { |
293 | if (!access_ok(check, WINREG_ADDR(reg - 16), size)) | 292 | if (!access_ok(WINREG_ADDR(reg - 16), size)) |
294 | return -EFAULT; | 293 | return -EFAULT; |
295 | } | 294 | } |
296 | reg = (insn >> 14) & 0x1f; | 295 | reg = (insn >> 14) & 0x1f; |
297 | if (reg >= 16) { | 296 | if (reg >= 16) { |
298 | if (!access_ok(check, WINREG_ADDR(reg - 16), size)) | 297 | if (!access_ok(WINREG_ADDR(reg - 16), size)) |
299 | return -EFAULT; | 298 | return -EFAULT; |
300 | } | 299 | } |
301 | if (!(insn & 0x2000)) { | 300 | if (!(insn & 0x2000)) { |
302 | reg = (insn & 0x1f); | 301 | reg = (insn & 0x1f); |
303 | if (reg >= 16) { | 302 | if (reg >= 16) { |
304 | if (!access_ok(check, WINREG_ADDR(reg - 16), size)) | 303 | if (!access_ok(WINREG_ADDR(reg - 16), size)) |
305 | return -EFAULT; | 304 | return -EFAULT; |
306 | } | 305 | } |
307 | } | 306 | } |
diff --git a/arch/um/kernel/ptrace.c b/arch/um/kernel/ptrace.c index 1a1d88a4d940..5f47422401e1 100644 --- a/arch/um/kernel/ptrace.c +++ b/arch/um/kernel/ptrace.c | |||
@@ -66,7 +66,7 @@ long arch_ptrace(struct task_struct *child, long request, | |||
66 | 66 | ||
67 | #ifdef PTRACE_GETREGS | 67 | #ifdef PTRACE_GETREGS |
68 | case PTRACE_GETREGS: { /* Get all gp regs from the child. */ | 68 | case PTRACE_GETREGS: { /* Get all gp regs from the child. */ |
69 | if (!access_ok(VERIFY_WRITE, p, MAX_REG_OFFSET)) { | 69 | if (!access_ok(p, MAX_REG_OFFSET)) { |
70 | ret = -EIO; | 70 | ret = -EIO; |
71 | break; | 71 | break; |
72 | } | 72 | } |
@@ -81,7 +81,7 @@ long arch_ptrace(struct task_struct *child, long request, | |||
81 | #ifdef PTRACE_SETREGS | 81 | #ifdef PTRACE_SETREGS |
82 | case PTRACE_SETREGS: { /* Set all gp regs in the child. */ | 82 | case PTRACE_SETREGS: { /* Set all gp regs in the child. */ |
83 | unsigned long tmp = 0; | 83 | unsigned long tmp = 0; |
84 | if (!access_ok(VERIFY_READ, p, MAX_REG_OFFSET)) { | 84 | if (!access_ok(p, MAX_REG_OFFSET)) { |
85 | ret = -EIO; | 85 | ret = -EIO; |
86 | break; | 86 | break; |
87 | } | 87 | } |
diff --git a/arch/unicore32/kernel/signal.c b/arch/unicore32/kernel/signal.c index 4ae51cf15ade..63be04809d40 100644 --- a/arch/unicore32/kernel/signal.c +++ b/arch/unicore32/kernel/signal.c | |||
@@ -117,7 +117,7 @@ asmlinkage int __sys_rt_sigreturn(struct pt_regs *regs) | |||
117 | 117 | ||
118 | frame = (struct rt_sigframe __user *)regs->UCreg_sp; | 118 | frame = (struct rt_sigframe __user *)regs->UCreg_sp; |
119 | 119 | ||
120 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 120 | if (!access_ok(frame, sizeof(*frame))) |
121 | goto badframe; | 121 | goto badframe; |
122 | 122 | ||
123 | if (restore_sigframe(regs, &frame->sig)) | 123 | if (restore_sigframe(regs, &frame->sig)) |
@@ -205,7 +205,7 @@ static inline void __user *get_sigframe(struct k_sigaction *ka, | |||
205 | /* | 205 | /* |
206 | * Check that we can actually write to the signal frame. | 206 | * Check that we can actually write to the signal frame. |
207 | */ | 207 | */ |
208 | if (!access_ok(VERIFY_WRITE, frame, framesize)) | 208 | if (!access_ok(frame, framesize)) |
209 | frame = NULL; | 209 | frame = NULL; |
210 | 210 | ||
211 | return frame; | 211 | return frame; |
diff --git a/arch/x86/entry/vsyscall/vsyscall_64.c b/arch/x86/entry/vsyscall/vsyscall_64.c index d78bcc03e60e..d9d81ad7a400 100644 --- a/arch/x86/entry/vsyscall/vsyscall_64.c +++ b/arch/x86/entry/vsyscall/vsyscall_64.c | |||
@@ -99,7 +99,7 @@ static bool write_ok_or_segv(unsigned long ptr, size_t size) | |||
99 | * sig_on_uaccess_err, this could go away. | 99 | * sig_on_uaccess_err, this could go away. |
100 | */ | 100 | */ |
101 | 101 | ||
102 | if (!access_ok(VERIFY_WRITE, (void __user *)ptr, size)) { | 102 | if (!access_ok((void __user *)ptr, size)) { |
103 | struct thread_struct *thread = ¤t->thread; | 103 | struct thread_struct *thread = ¤t->thread; |
104 | 104 | ||
105 | thread->error_code = X86_PF_USER | X86_PF_WRITE; | 105 | thread->error_code = X86_PF_USER | X86_PF_WRITE; |
diff --git a/arch/x86/ia32/ia32_aout.c b/arch/x86/ia32/ia32_aout.c index 8e02b30cf08e..f65b78d32f5e 100644 --- a/arch/x86/ia32/ia32_aout.c +++ b/arch/x86/ia32/ia32_aout.c | |||
@@ -176,10 +176,10 @@ static int aout_core_dump(struct coredump_params *cprm) | |||
176 | 176 | ||
177 | /* make sure we actually have a data and stack area to dump */ | 177 | /* make sure we actually have a data and stack area to dump */ |
178 | set_fs(USER_DS); | 178 | set_fs(USER_DS); |
179 | if (!access_ok(VERIFY_READ, (void *) (unsigned long)START_DATA(dump), | 179 | if (!access_ok((void *) (unsigned long)START_DATA(dump), |
180 | dump.u_dsize << PAGE_SHIFT)) | 180 | dump.u_dsize << PAGE_SHIFT)) |
181 | dump.u_dsize = 0; | 181 | dump.u_dsize = 0; |
182 | if (!access_ok(VERIFY_READ, (void *) (unsigned long)START_STACK(dump), | 182 | if (!access_ok((void *) (unsigned long)START_STACK(dump), |
183 | dump.u_ssize << PAGE_SHIFT)) | 183 | dump.u_ssize << PAGE_SHIFT)) |
184 | dump.u_ssize = 0; | 184 | dump.u_ssize = 0; |
185 | 185 | ||
diff --git a/arch/x86/ia32/ia32_signal.c b/arch/x86/ia32/ia32_signal.c index 86b1341cba9a..321fe5f5d0e9 100644 --- a/arch/x86/ia32/ia32_signal.c +++ b/arch/x86/ia32/ia32_signal.c | |||
@@ -119,7 +119,7 @@ asmlinkage long sys32_sigreturn(void) | |||
119 | struct sigframe_ia32 __user *frame = (struct sigframe_ia32 __user *)(regs->sp-8); | 119 | struct sigframe_ia32 __user *frame = (struct sigframe_ia32 __user *)(regs->sp-8); |
120 | sigset_t set; | 120 | sigset_t set; |
121 | 121 | ||
122 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 122 | if (!access_ok(frame, sizeof(*frame))) |
123 | goto badframe; | 123 | goto badframe; |
124 | if (__get_user(set.sig[0], &frame->sc.oldmask) | 124 | if (__get_user(set.sig[0], &frame->sc.oldmask) |
125 | || (_COMPAT_NSIG_WORDS > 1 | 125 | || (_COMPAT_NSIG_WORDS > 1 |
@@ -147,7 +147,7 @@ asmlinkage long sys32_rt_sigreturn(void) | |||
147 | 147 | ||
148 | frame = (struct rt_sigframe_ia32 __user *)(regs->sp - 4); | 148 | frame = (struct rt_sigframe_ia32 __user *)(regs->sp - 4); |
149 | 149 | ||
150 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 150 | if (!access_ok(frame, sizeof(*frame))) |
151 | goto badframe; | 151 | goto badframe; |
152 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) | 152 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) |
153 | goto badframe; | 153 | goto badframe; |
@@ -269,7 +269,7 @@ int ia32_setup_frame(int sig, struct ksignal *ksig, | |||
269 | 269 | ||
270 | frame = get_sigframe(ksig, regs, sizeof(*frame), &fpstate); | 270 | frame = get_sigframe(ksig, regs, sizeof(*frame), &fpstate); |
271 | 271 | ||
272 | if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame))) | 272 | if (!access_ok(frame, sizeof(*frame))) |
273 | return -EFAULT; | 273 | return -EFAULT; |
274 | 274 | ||
275 | if (__put_user(sig, &frame->sig)) | 275 | if (__put_user(sig, &frame->sig)) |
@@ -349,7 +349,7 @@ int ia32_setup_rt_frame(int sig, struct ksignal *ksig, | |||
349 | 349 | ||
350 | frame = get_sigframe(ksig, regs, sizeof(*frame), &fpstate); | 350 | frame = get_sigframe(ksig, regs, sizeof(*frame), &fpstate); |
351 | 351 | ||
352 | if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame))) | 352 | if (!access_ok(frame, sizeof(*frame))) |
353 | return -EFAULT; | 353 | return -EFAULT; |
354 | 354 | ||
355 | put_user_try { | 355 | put_user_try { |
diff --git a/arch/x86/ia32/sys_ia32.c b/arch/x86/ia32/sys_ia32.c index 11ef7b7c9cc8..a43212036257 100644 --- a/arch/x86/ia32/sys_ia32.c +++ b/arch/x86/ia32/sys_ia32.c | |||
@@ -75,7 +75,7 @@ static int cp_stat64(struct stat64 __user *ubuf, struct kstat *stat) | |||
75 | typeof(ubuf->st_gid) gid = 0; | 75 | typeof(ubuf->st_gid) gid = 0; |
76 | SET_UID(uid, from_kuid_munged(current_user_ns(), stat->uid)); | 76 | SET_UID(uid, from_kuid_munged(current_user_ns(), stat->uid)); |
77 | SET_GID(gid, from_kgid_munged(current_user_ns(), stat->gid)); | 77 | SET_GID(gid, from_kgid_munged(current_user_ns(), stat->gid)); |
78 | if (!access_ok(VERIFY_WRITE, ubuf, sizeof(struct stat64)) || | 78 | if (!access_ok(ubuf, sizeof(struct stat64)) || |
79 | __put_user(huge_encode_dev(stat->dev), &ubuf->st_dev) || | 79 | __put_user(huge_encode_dev(stat->dev), &ubuf->st_dev) || |
80 | __put_user(stat->ino, &ubuf->__st_ino) || | 80 | __put_user(stat->ino, &ubuf->__st_ino) || |
81 | __put_user(stat->ino, &ubuf->st_ino) || | 81 | __put_user(stat->ino, &ubuf->st_ino) || |
diff --git a/arch/x86/include/asm/checksum_32.h b/arch/x86/include/asm/checksum_32.h index 7a659c74cd03..f57b94e02c57 100644 --- a/arch/x86/include/asm/checksum_32.h +++ b/arch/x86/include/asm/checksum_32.h | |||
@@ -182,7 +182,7 @@ static inline __wsum csum_and_copy_to_user(const void *src, | |||
182 | __wsum ret; | 182 | __wsum ret; |
183 | 183 | ||
184 | might_sleep(); | 184 | might_sleep(); |
185 | if (access_ok(VERIFY_WRITE, dst, len)) { | 185 | if (access_ok(dst, len)) { |
186 | stac(); | 186 | stac(); |
187 | ret = csum_partial_copy_generic(src, (__force void *)dst, | 187 | ret = csum_partial_copy_generic(src, (__force void *)dst, |
188 | len, sum, NULL, err_ptr); | 188 | len, sum, NULL, err_ptr); |
diff --git a/arch/x86/include/asm/io.h b/arch/x86/include/asm/io.h index 832da8229cc7..686247db3106 100644 --- a/arch/x86/include/asm/io.h +++ b/arch/x86/include/asm/io.h | |||
@@ -221,6 +221,14 @@ extern void set_iounmap_nonlazy(void); | |||
221 | 221 | ||
222 | #ifdef __KERNEL__ | 222 | #ifdef __KERNEL__ |
223 | 223 | ||
224 | void memcpy_fromio(void *, const volatile void __iomem *, size_t); | ||
225 | void memcpy_toio(volatile void __iomem *, const void *, size_t); | ||
226 | void memset_io(volatile void __iomem *, int, size_t); | ||
227 | |||
228 | #define memcpy_fromio memcpy_fromio | ||
229 | #define memcpy_toio memcpy_toio | ||
230 | #define memset_io memset_io | ||
231 | |||
224 | #include <asm-generic/iomap.h> | 232 | #include <asm-generic/iomap.h> |
225 | 233 | ||
226 | /* | 234 | /* |
diff --git a/arch/x86/include/asm/pgtable_32.h b/arch/x86/include/asm/pgtable_32.h index b3ec519e3982..4fe9e7fc74d3 100644 --- a/arch/x86/include/asm/pgtable_32.h +++ b/arch/x86/include/asm/pgtable_32.h | |||
@@ -37,7 +37,7 @@ void sync_initial_page_table(void); | |||
37 | /* | 37 | /* |
38 | * Define this if things work differently on an i386 and an i486: | 38 | * Define this if things work differently on an i386 and an i486: |
39 | * it will (on an i486) warn about kernel memory accesses that are | 39 | * it will (on an i486) warn about kernel memory accesses that are |
40 | * done without a 'access_ok(VERIFY_WRITE,..)' | 40 | * done without a 'access_ok( ..)' |
41 | */ | 41 | */ |
42 | #undef TEST_ACCESS_OK | 42 | #undef TEST_ACCESS_OK |
43 | 43 | ||
diff --git a/arch/x86/include/asm/string_64.h b/arch/x86/include/asm/string_64.h index 7ad41bfcc16c..4e4194e21a09 100644 --- a/arch/x86/include/asm/string_64.h +++ b/arch/x86/include/asm/string_64.h | |||
@@ -7,24 +7,6 @@ | |||
7 | 7 | ||
8 | /* Written 2002 by Andi Kleen */ | 8 | /* Written 2002 by Andi Kleen */ |
9 | 9 | ||
10 | /* Only used for special circumstances. Stolen from i386/string.h */ | ||
11 | static __always_inline void *__inline_memcpy(void *to, const void *from, size_t n) | ||
12 | { | ||
13 | unsigned long d0, d1, d2; | ||
14 | asm volatile("rep ; movsl\n\t" | ||
15 | "testb $2,%b4\n\t" | ||
16 | "je 1f\n\t" | ||
17 | "movsw\n" | ||
18 | "1:\ttestb $1,%b4\n\t" | ||
19 | "je 2f\n\t" | ||
20 | "movsb\n" | ||
21 | "2:" | ||
22 | : "=&c" (d0), "=&D" (d1), "=&S" (d2) | ||
23 | : "0" (n / 4), "q" (n), "1" ((long)to), "2" ((long)from) | ||
24 | : "memory"); | ||
25 | return to; | ||
26 | } | ||
27 | |||
28 | /* Even with __builtin_ the compiler may decide to use the out of line | 10 | /* Even with __builtin_ the compiler may decide to use the out of line |
29 | function. */ | 11 | function. */ |
30 | 12 | ||
diff --git a/arch/x86/include/asm/uaccess.h b/arch/x86/include/asm/uaccess.h index b5e58cc0c5e7..a77445d1b034 100644 --- a/arch/x86/include/asm/uaccess.h +++ b/arch/x86/include/asm/uaccess.h | |||
@@ -77,9 +77,6 @@ static inline bool __chk_range_not_ok(unsigned long addr, unsigned long size, un | |||
77 | 77 | ||
78 | /** | 78 | /** |
79 | * access_ok: - Checks if a user space pointer is valid | 79 | * access_ok: - Checks if a user space pointer is valid |
80 | * @type: Type of access: %VERIFY_READ or %VERIFY_WRITE. Note that | ||
81 | * %VERIFY_WRITE is a superset of %VERIFY_READ - if it is safe | ||
82 | * to write to a block, it is always safe to read from it. | ||
83 | * @addr: User space pointer to start of block to check | 80 | * @addr: User space pointer to start of block to check |
84 | * @size: Size of block to check | 81 | * @size: Size of block to check |
85 | * | 82 | * |
@@ -95,7 +92,7 @@ static inline bool __chk_range_not_ok(unsigned long addr, unsigned long size, un | |||
95 | * checks that the pointer is in the user space range - after calling | 92 | * checks that the pointer is in the user space range - after calling |
96 | * this function, memory access functions may still return -EFAULT. | 93 | * this function, memory access functions may still return -EFAULT. |
97 | */ | 94 | */ |
98 | #define access_ok(type, addr, size) \ | 95 | #define access_ok(addr, size) \ |
99 | ({ \ | 96 | ({ \ |
100 | WARN_ON_IN_IRQ(); \ | 97 | WARN_ON_IN_IRQ(); \ |
101 | likely(!__range_not_ok(addr, size, user_addr_max())); \ | 98 | likely(!__range_not_ok(addr, size, user_addr_max())); \ |
@@ -189,19 +186,14 @@ __typeof__(__builtin_choose_expr(sizeof(x) > sizeof(0UL), 0ULL, 0UL)) | |||
189 | 186 | ||
190 | 187 | ||
191 | #ifdef CONFIG_X86_32 | 188 | #ifdef CONFIG_X86_32 |
192 | #define __put_user_asm_u64(x, addr, err, errret) \ | 189 | #define __put_user_goto_u64(x, addr, label) \ |
193 | asm volatile("\n" \ | 190 | asm_volatile_goto("\n" \ |
194 | "1: movl %%eax,0(%2)\n" \ | 191 | "1: movl %%eax,0(%1)\n" \ |
195 | "2: movl %%edx,4(%2)\n" \ | 192 | "2: movl %%edx,4(%1)\n" \ |
196 | "3:" \ | 193 | _ASM_EXTABLE_UA(1b, %l2) \ |
197 | ".section .fixup,\"ax\"\n" \ | 194 | _ASM_EXTABLE_UA(2b, %l2) \ |
198 | "4: movl %3,%0\n" \ | 195 | : : "A" (x), "r" (addr) \ |
199 | " jmp 3b\n" \ | 196 | : : label) |
200 | ".previous\n" \ | ||
201 | _ASM_EXTABLE_UA(1b, 4b) \ | ||
202 | _ASM_EXTABLE_UA(2b, 4b) \ | ||
203 | : "=r" (err) \ | ||
204 | : "A" (x), "r" (addr), "i" (errret), "0" (err)) | ||
205 | 197 | ||
206 | #define __put_user_asm_ex_u64(x, addr) \ | 198 | #define __put_user_asm_ex_u64(x, addr) \ |
207 | asm volatile("\n" \ | 199 | asm volatile("\n" \ |
@@ -216,8 +208,8 @@ __typeof__(__builtin_choose_expr(sizeof(x) > sizeof(0UL), 0ULL, 0UL)) | |||
216 | asm volatile("call __put_user_8" : "=a" (__ret_pu) \ | 208 | asm volatile("call __put_user_8" : "=a" (__ret_pu) \ |
217 | : "A" ((typeof(*(ptr)))(x)), "c" (ptr) : "ebx") | 209 | : "A" ((typeof(*(ptr)))(x)), "c" (ptr) : "ebx") |
218 | #else | 210 | #else |
219 | #define __put_user_asm_u64(x, ptr, retval, errret) \ | 211 | #define __put_user_goto_u64(x, ptr, label) \ |
220 | __put_user_asm(x, ptr, retval, "q", "", "er", errret) | 212 | __put_user_goto(x, ptr, "q", "", "er", label) |
221 | #define __put_user_asm_ex_u64(x, addr) \ | 213 | #define __put_user_asm_ex_u64(x, addr) \ |
222 | __put_user_asm_ex(x, addr, "q", "", "er") | 214 | __put_user_asm_ex(x, addr, "q", "", "er") |
223 | #define __put_user_x8(x, ptr, __ret_pu) __put_user_x(8, x, ptr, __ret_pu) | 215 | #define __put_user_x8(x, ptr, __ret_pu) __put_user_x(8, x, ptr, __ret_pu) |
@@ -278,23 +270,21 @@ extern void __put_user_8(void); | |||
278 | __builtin_expect(__ret_pu, 0); \ | 270 | __builtin_expect(__ret_pu, 0); \ |
279 | }) | 271 | }) |
280 | 272 | ||
281 | #define __put_user_size(x, ptr, size, retval, errret) \ | 273 | #define __put_user_size(x, ptr, size, label) \ |
282 | do { \ | 274 | do { \ |
283 | retval = 0; \ | ||
284 | __chk_user_ptr(ptr); \ | 275 | __chk_user_ptr(ptr); \ |
285 | switch (size) { \ | 276 | switch (size) { \ |
286 | case 1: \ | 277 | case 1: \ |
287 | __put_user_asm(x, ptr, retval, "b", "b", "iq", errret); \ | 278 | __put_user_goto(x, ptr, "b", "b", "iq", label); \ |
288 | break; \ | 279 | break; \ |
289 | case 2: \ | 280 | case 2: \ |
290 | __put_user_asm(x, ptr, retval, "w", "w", "ir", errret); \ | 281 | __put_user_goto(x, ptr, "w", "w", "ir", label); \ |
291 | break; \ | 282 | break; \ |
292 | case 4: \ | 283 | case 4: \ |
293 | __put_user_asm(x, ptr, retval, "l", "k", "ir", errret); \ | 284 | __put_user_goto(x, ptr, "l", "k", "ir", label); \ |
294 | break; \ | 285 | break; \ |
295 | case 8: \ | 286 | case 8: \ |
296 | __put_user_asm_u64((__typeof__(*ptr))(x), ptr, retval, \ | 287 | __put_user_goto_u64((__typeof__(*ptr))(x), ptr, label); \ |
297 | errret); \ | ||
298 | break; \ | 288 | break; \ |
299 | default: \ | 289 | default: \ |
300 | __put_user_bad(); \ | 290 | __put_user_bad(); \ |
@@ -439,9 +429,12 @@ do { \ | |||
439 | 429 | ||
440 | #define __put_user_nocheck(x, ptr, size) \ | 430 | #define __put_user_nocheck(x, ptr, size) \ |
441 | ({ \ | 431 | ({ \ |
442 | int __pu_err; \ | 432 | __label__ __pu_label; \ |
433 | int __pu_err = -EFAULT; \ | ||
443 | __uaccess_begin(); \ | 434 | __uaccess_begin(); \ |
444 | __put_user_size((x), (ptr), (size), __pu_err, -EFAULT); \ | 435 | __put_user_size((x), (ptr), (size), __pu_label); \ |
436 | __pu_err = 0; \ | ||
437 | __pu_label: \ | ||
445 | __uaccess_end(); \ | 438 | __uaccess_end(); \ |
446 | __builtin_expect(__pu_err, 0); \ | 439 | __builtin_expect(__pu_err, 0); \ |
447 | }) | 440 | }) |
@@ -466,17 +459,23 @@ struct __large_struct { unsigned long buf[100]; }; | |||
466 | * we do not write to any memory gcc knows about, so there are no | 459 | * we do not write to any memory gcc knows about, so there are no |
467 | * aliasing issues. | 460 | * aliasing issues. |
468 | */ | 461 | */ |
469 | #define __put_user_asm(x, addr, err, itype, rtype, ltype, errret) \ | 462 | #define __put_user_goto(x, addr, itype, rtype, ltype, label) \ |
470 | asm volatile("\n" \ | 463 | asm_volatile_goto("\n" \ |
471 | "1: mov"itype" %"rtype"1,%2\n" \ | 464 | "1: mov"itype" %"rtype"0,%1\n" \ |
472 | "2:\n" \ | 465 | _ASM_EXTABLE_UA(1b, %l2) \ |
473 | ".section .fixup,\"ax\"\n" \ | 466 | : : ltype(x), "m" (__m(addr)) \ |
474 | "3: mov %3,%0\n" \ | 467 | : : label) |
475 | " jmp 2b\n" \ | 468 | |
476 | ".previous\n" \ | 469 | #define __put_user_failed(x, addr, itype, rtype, ltype, errret) \ |
477 | _ASM_EXTABLE_UA(1b, 3b) \ | 470 | ({ __label__ __puflab; \ |
478 | : "=r"(err) \ | 471 | int __pufret = errret; \ |
479 | : ltype(x), "m" (__m(addr)), "i" (errret), "0" (err)) | 472 | __put_user_goto(x,addr,itype,rtype,ltype,__puflab); \ |
473 | __pufret = 0; \ | ||
474 | __puflab: __pufret; }) | ||
475 | |||
476 | #define __put_user_asm(x, addr, retval, itype, rtype, ltype, errret) do { \ | ||
477 | retval = __put_user_failed(x, addr, itype, rtype, ltype, errret); \ | ||
478 | } while (0) | ||
480 | 479 | ||
481 | #define __put_user_asm_ex(x, addr, itype, rtype, ltype) \ | 480 | #define __put_user_asm_ex(x, addr, itype, rtype, ltype) \ |
482 | asm volatile("1: mov"itype" %"rtype"0,%1\n" \ | 481 | asm volatile("1: mov"itype" %"rtype"0,%1\n" \ |
@@ -670,7 +669,7 @@ extern void __cmpxchg_wrong_size(void) | |||
670 | 669 | ||
671 | #define user_atomic_cmpxchg_inatomic(uval, ptr, old, new) \ | 670 | #define user_atomic_cmpxchg_inatomic(uval, ptr, old, new) \ |
672 | ({ \ | 671 | ({ \ |
673 | access_ok(VERIFY_WRITE, (ptr), sizeof(*(ptr))) ? \ | 672 | access_ok((ptr), sizeof(*(ptr))) ? \ |
674 | __user_atomic_cmpxchg_inatomic((uval), (ptr), \ | 673 | __user_atomic_cmpxchg_inatomic((uval), (ptr), \ |
675 | (old), (new), sizeof(*(ptr))) : \ | 674 | (old), (new), sizeof(*(ptr))) : \ |
676 | -EFAULT; \ | 675 | -EFAULT; \ |
@@ -708,16 +707,18 @@ extern struct movsl_mask { | |||
708 | * checking before using them, but you have to surround them with the | 707 | * checking before using them, but you have to surround them with the |
709 | * user_access_begin/end() pair. | 708 | * user_access_begin/end() pair. |
710 | */ | 709 | */ |
711 | #define user_access_begin() __uaccess_begin() | 710 | static __must_check inline bool user_access_begin(const void __user *ptr, size_t len) |
711 | { | ||
712 | if (unlikely(!access_ok(ptr,len))) | ||
713 | return 0; | ||
714 | __uaccess_begin(); | ||
715 | return 1; | ||
716 | } | ||
717 | #define user_access_begin(a,b) user_access_begin(a,b) | ||
712 | #define user_access_end() __uaccess_end() | 718 | #define user_access_end() __uaccess_end() |
713 | 719 | ||
714 | #define unsafe_put_user(x, ptr, err_label) \ | 720 | #define unsafe_put_user(x, ptr, label) \ |
715 | do { \ | 721 | __put_user_size((__typeof__(*(ptr)))(x), (ptr), sizeof(*(ptr)), label) |
716 | int __pu_err; \ | ||
717 | __typeof__(*(ptr)) __pu_val = (x); \ | ||
718 | __put_user_size(__pu_val, (ptr), sizeof(*(ptr)), __pu_err, -EFAULT); \ | ||
719 | if (unlikely(__pu_err)) goto err_label; \ | ||
720 | } while (0) | ||
721 | 722 | ||
722 | #define unsafe_get_user(x, ptr, err_label) \ | 723 | #define unsafe_get_user(x, ptr, err_label) \ |
723 | do { \ | 724 | do { \ |
diff --git a/arch/x86/kernel/fpu/signal.c b/arch/x86/kernel/fpu/signal.c index d99a8ee9e185..f6a1d299627c 100644 --- a/arch/x86/kernel/fpu/signal.c +++ b/arch/x86/kernel/fpu/signal.c | |||
@@ -164,7 +164,7 @@ int copy_fpstate_to_sigframe(void __user *buf, void __user *buf_fx, int size) | |||
164 | ia32_fxstate &= (IS_ENABLED(CONFIG_X86_32) || | 164 | ia32_fxstate &= (IS_ENABLED(CONFIG_X86_32) || |
165 | IS_ENABLED(CONFIG_IA32_EMULATION)); | 165 | IS_ENABLED(CONFIG_IA32_EMULATION)); |
166 | 166 | ||
167 | if (!access_ok(VERIFY_WRITE, buf, size)) | 167 | if (!access_ok(buf, size)) |
168 | return -EACCES; | 168 | return -EACCES; |
169 | 169 | ||
170 | if (!static_cpu_has(X86_FEATURE_FPU)) | 170 | if (!static_cpu_has(X86_FEATURE_FPU)) |
@@ -281,7 +281,7 @@ static int __fpu__restore_sig(void __user *buf, void __user *buf_fx, int size) | |||
281 | return 0; | 281 | return 0; |
282 | } | 282 | } |
283 | 283 | ||
284 | if (!access_ok(VERIFY_READ, buf, size)) | 284 | if (!access_ok(buf, size)) |
285 | return -EACCES; | 285 | return -EACCES; |
286 | 286 | ||
287 | fpu__initialize(fpu); | 287 | fpu__initialize(fpu); |
diff --git a/arch/x86/kernel/signal.c b/arch/x86/kernel/signal.c index 92a3b312a53c..08dfd4c1a4f9 100644 --- a/arch/x86/kernel/signal.c +++ b/arch/x86/kernel/signal.c | |||
@@ -322,7 +322,7 @@ __setup_frame(int sig, struct ksignal *ksig, sigset_t *set, | |||
322 | 322 | ||
323 | frame = get_sigframe(&ksig->ka, regs, sizeof(*frame), &fpstate); | 323 | frame = get_sigframe(&ksig->ka, regs, sizeof(*frame), &fpstate); |
324 | 324 | ||
325 | if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame))) | 325 | if (!access_ok(frame, sizeof(*frame))) |
326 | return -EFAULT; | 326 | return -EFAULT; |
327 | 327 | ||
328 | if (__put_user(sig, &frame->sig)) | 328 | if (__put_user(sig, &frame->sig)) |
@@ -385,7 +385,7 @@ static int __setup_rt_frame(int sig, struct ksignal *ksig, | |||
385 | 385 | ||
386 | frame = get_sigframe(&ksig->ka, regs, sizeof(*frame), &fpstate); | 386 | frame = get_sigframe(&ksig->ka, regs, sizeof(*frame), &fpstate); |
387 | 387 | ||
388 | if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame))) | 388 | if (!access_ok(frame, sizeof(*frame))) |
389 | return -EFAULT; | 389 | return -EFAULT; |
390 | 390 | ||
391 | put_user_try { | 391 | put_user_try { |
@@ -465,7 +465,7 @@ static int __setup_rt_frame(int sig, struct ksignal *ksig, | |||
465 | 465 | ||
466 | frame = get_sigframe(&ksig->ka, regs, sizeof(struct rt_sigframe), &fp); | 466 | frame = get_sigframe(&ksig->ka, regs, sizeof(struct rt_sigframe), &fp); |
467 | 467 | ||
468 | if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame))) | 468 | if (!access_ok(frame, sizeof(*frame))) |
469 | return -EFAULT; | 469 | return -EFAULT; |
470 | 470 | ||
471 | if (ksig->ka.sa.sa_flags & SA_SIGINFO) { | 471 | if (ksig->ka.sa.sa_flags & SA_SIGINFO) { |
@@ -547,7 +547,7 @@ static int x32_setup_rt_frame(struct ksignal *ksig, | |||
547 | 547 | ||
548 | frame = get_sigframe(&ksig->ka, regs, sizeof(*frame), &fpstate); | 548 | frame = get_sigframe(&ksig->ka, regs, sizeof(*frame), &fpstate); |
549 | 549 | ||
550 | if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame))) | 550 | if (!access_ok(frame, sizeof(*frame))) |
551 | return -EFAULT; | 551 | return -EFAULT; |
552 | 552 | ||
553 | if (ksig->ka.sa.sa_flags & SA_SIGINFO) { | 553 | if (ksig->ka.sa.sa_flags & SA_SIGINFO) { |
@@ -610,7 +610,7 @@ SYSCALL_DEFINE0(sigreturn) | |||
610 | 610 | ||
611 | frame = (struct sigframe __user *)(regs->sp - 8); | 611 | frame = (struct sigframe __user *)(regs->sp - 8); |
612 | 612 | ||
613 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 613 | if (!access_ok(frame, sizeof(*frame))) |
614 | goto badframe; | 614 | goto badframe; |
615 | if (__get_user(set.sig[0], &frame->sc.oldmask) || (_NSIG_WORDS > 1 | 615 | if (__get_user(set.sig[0], &frame->sc.oldmask) || (_NSIG_WORDS > 1 |
616 | && __copy_from_user(&set.sig[1], &frame->extramask, | 616 | && __copy_from_user(&set.sig[1], &frame->extramask, |
@@ -642,7 +642,7 @@ SYSCALL_DEFINE0(rt_sigreturn) | |||
642 | unsigned long uc_flags; | 642 | unsigned long uc_flags; |
643 | 643 | ||
644 | frame = (struct rt_sigframe __user *)(regs->sp - sizeof(long)); | 644 | frame = (struct rt_sigframe __user *)(regs->sp - sizeof(long)); |
645 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 645 | if (!access_ok(frame, sizeof(*frame))) |
646 | goto badframe; | 646 | goto badframe; |
647 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) | 647 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) |
648 | goto badframe; | 648 | goto badframe; |
@@ -871,7 +871,7 @@ asmlinkage long sys32_x32_rt_sigreturn(void) | |||
871 | 871 | ||
872 | frame = (struct rt_sigframe_x32 __user *)(regs->sp - 8); | 872 | frame = (struct rt_sigframe_x32 __user *)(regs->sp - 8); |
873 | 873 | ||
874 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 874 | if (!access_ok(frame, sizeof(*frame))) |
875 | goto badframe; | 875 | goto badframe; |
876 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) | 876 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) |
877 | goto badframe; | 877 | goto badframe; |
diff --git a/arch/x86/kernel/stacktrace.c b/arch/x86/kernel/stacktrace.c index 7627455047c2..5c2d71a1dc06 100644 --- a/arch/x86/kernel/stacktrace.c +++ b/arch/x86/kernel/stacktrace.c | |||
@@ -177,7 +177,7 @@ copy_stack_frame(const void __user *fp, struct stack_frame_user *frame) | |||
177 | { | 177 | { |
178 | int ret; | 178 | int ret; |
179 | 179 | ||
180 | if (!access_ok(VERIFY_READ, fp, sizeof(*frame))) | 180 | if (!access_ok(fp, sizeof(*frame))) |
181 | return 0; | 181 | return 0; |
182 | 182 | ||
183 | ret = 1; | 183 | ret = 1; |
diff --git a/arch/x86/kernel/vm86_32.c b/arch/x86/kernel/vm86_32.c index c2fd39752da8..a092b6b40c6b 100644 --- a/arch/x86/kernel/vm86_32.c +++ b/arch/x86/kernel/vm86_32.c | |||
@@ -114,7 +114,7 @@ void save_v86_state(struct kernel_vm86_regs *regs, int retval) | |||
114 | set_flags(regs->pt.flags, VEFLAGS, X86_EFLAGS_VIF | vm86->veflags_mask); | 114 | set_flags(regs->pt.flags, VEFLAGS, X86_EFLAGS_VIF | vm86->veflags_mask); |
115 | user = vm86->user_vm86; | 115 | user = vm86->user_vm86; |
116 | 116 | ||
117 | if (!access_ok(VERIFY_WRITE, user, vm86->vm86plus.is_vm86pus ? | 117 | if (!access_ok(user, vm86->vm86plus.is_vm86pus ? |
118 | sizeof(struct vm86plus_struct) : | 118 | sizeof(struct vm86plus_struct) : |
119 | sizeof(struct vm86_struct))) { | 119 | sizeof(struct vm86_struct))) { |
120 | pr_alert("could not access userspace vm86 info\n"); | 120 | pr_alert("could not access userspace vm86 info\n"); |
@@ -278,7 +278,7 @@ static long do_sys_vm86(struct vm86plus_struct __user *user_vm86, bool plus) | |||
278 | if (vm86->saved_sp0) | 278 | if (vm86->saved_sp0) |
279 | return -EPERM; | 279 | return -EPERM; |
280 | 280 | ||
281 | if (!access_ok(VERIFY_READ, user_vm86, plus ? | 281 | if (!access_ok(user_vm86, plus ? |
282 | sizeof(struct vm86_struct) : | 282 | sizeof(struct vm86_struct) : |
283 | sizeof(struct vm86plus_struct))) | 283 | sizeof(struct vm86plus_struct))) |
284 | return -EFAULT; | 284 | return -EFAULT; |
diff --git a/arch/x86/lib/Makefile b/arch/x86/lib/Makefile index 25a972c61b0a..ce28829f1281 100644 --- a/arch/x86/lib/Makefile +++ b/arch/x86/lib/Makefile | |||
@@ -30,6 +30,7 @@ lib-$(CONFIG_FUNCTION_ERROR_INJECTION) += error-inject.o | |||
30 | lib-$(CONFIG_RETPOLINE) += retpoline.o | 30 | lib-$(CONFIG_RETPOLINE) += retpoline.o |
31 | 31 | ||
32 | obj-y += msr.o msr-reg.o msr-reg-export.o hweight.o | 32 | obj-y += msr.o msr-reg.o msr-reg-export.o hweight.o |
33 | obj-y += iomem.o | ||
33 | 34 | ||
34 | ifeq ($(CONFIG_X86_32),y) | 35 | ifeq ($(CONFIG_X86_32),y) |
35 | obj-y += atomic64_32.o | 36 | obj-y += atomic64_32.o |
diff --git a/arch/x86/lib/csum-wrappers_64.c b/arch/x86/lib/csum-wrappers_64.c index 8bd53589ecfb..a6a2b7dccbff 100644 --- a/arch/x86/lib/csum-wrappers_64.c +++ b/arch/x86/lib/csum-wrappers_64.c | |||
@@ -27,7 +27,7 @@ csum_partial_copy_from_user(const void __user *src, void *dst, | |||
27 | might_sleep(); | 27 | might_sleep(); |
28 | *errp = 0; | 28 | *errp = 0; |
29 | 29 | ||
30 | if (!likely(access_ok(VERIFY_READ, src, len))) | 30 | if (!likely(access_ok(src, len))) |
31 | goto out_err; | 31 | goto out_err; |
32 | 32 | ||
33 | /* | 33 | /* |
@@ -89,7 +89,7 @@ csum_partial_copy_to_user(const void *src, void __user *dst, | |||
89 | 89 | ||
90 | might_sleep(); | 90 | might_sleep(); |
91 | 91 | ||
92 | if (unlikely(!access_ok(VERIFY_WRITE, dst, len))) { | 92 | if (unlikely(!access_ok(dst, len))) { |
93 | *errp = -EFAULT; | 93 | *errp = -EFAULT; |
94 | return 0; | 94 | return 0; |
95 | } | 95 | } |
diff --git a/arch/x86/lib/iomem.c b/arch/x86/lib/iomem.c new file mode 100644 index 000000000000..66894675f3c8 --- /dev/null +++ b/arch/x86/lib/iomem.c | |||
@@ -0,0 +1,42 @@ | |||
1 | #include <linux/string.h> | ||
2 | #include <linux/module.h> | ||
3 | #include <linux/io.h> | ||
4 | |||
5 | /* Originally from i386/string.h */ | ||
6 | static __always_inline void __iomem_memcpy(void *to, const void *from, size_t n) | ||
7 | { | ||
8 | unsigned long d0, d1, d2; | ||
9 | asm volatile("rep ; movsl\n\t" | ||
10 | "testb $2,%b4\n\t" | ||
11 | "je 1f\n\t" | ||
12 | "movsw\n" | ||
13 | "1:\ttestb $1,%b4\n\t" | ||
14 | "je 2f\n\t" | ||
15 | "movsb\n" | ||
16 | "2:" | ||
17 | : "=&c" (d0), "=&D" (d1), "=&S" (d2) | ||
18 | : "0" (n / 4), "q" (n), "1" ((long)to), "2" ((long)from) | ||
19 | : "memory"); | ||
20 | } | ||
21 | |||
22 | void memcpy_fromio(void *to, const volatile void __iomem *from, size_t n) | ||
23 | { | ||
24 | __iomem_memcpy(to, (const void *)from, n); | ||
25 | } | ||
26 | EXPORT_SYMBOL(memcpy_fromio); | ||
27 | |||
28 | void memcpy_toio(volatile void __iomem *to, const void *from, size_t n) | ||
29 | { | ||
30 | __iomem_memcpy((void *)to, (const void *) from, n); | ||
31 | } | ||
32 | EXPORT_SYMBOL(memcpy_toio); | ||
33 | |||
34 | void memset_io(volatile void __iomem *a, int b, size_t c) | ||
35 | { | ||
36 | /* | ||
37 | * TODO: memset can mangle the IO patterns quite a bit. | ||
38 | * perhaps it would be better to use a dumb one: | ||
39 | */ | ||
40 | memset((void *)a, b, c); | ||
41 | } | ||
42 | EXPORT_SYMBOL(memset_io); | ||
diff --git a/arch/x86/lib/usercopy_32.c b/arch/x86/lib/usercopy_32.c index 71fb58d44d58..bfd94e7812fc 100644 --- a/arch/x86/lib/usercopy_32.c +++ b/arch/x86/lib/usercopy_32.c | |||
@@ -67,7 +67,7 @@ unsigned long | |||
67 | clear_user(void __user *to, unsigned long n) | 67 | clear_user(void __user *to, unsigned long n) |
68 | { | 68 | { |
69 | might_fault(); | 69 | might_fault(); |
70 | if (access_ok(VERIFY_WRITE, to, n)) | 70 | if (access_ok(to, n)) |
71 | __do_clear_user(to, n); | 71 | __do_clear_user(to, n); |
72 | return n; | 72 | return n; |
73 | } | 73 | } |
diff --git a/arch/x86/lib/usercopy_64.c b/arch/x86/lib/usercopy_64.c index 1bd837cdc4b1..ee42bb0cbeb3 100644 --- a/arch/x86/lib/usercopy_64.c +++ b/arch/x86/lib/usercopy_64.c | |||
@@ -48,7 +48,7 @@ EXPORT_SYMBOL(__clear_user); | |||
48 | 48 | ||
49 | unsigned long clear_user(void __user *to, unsigned long n) | 49 | unsigned long clear_user(void __user *to, unsigned long n) |
50 | { | 50 | { |
51 | if (access_ok(VERIFY_WRITE, to, n)) | 51 | if (access_ok(to, n)) |
52 | return __clear_user(to, n); | 52 | return __clear_user(to, n); |
53 | return n; | 53 | return n; |
54 | } | 54 | } |
diff --git a/arch/x86/math-emu/fpu_system.h b/arch/x86/math-emu/fpu_system.h index c8b1b31ed7c4..f98a0c956764 100644 --- a/arch/x86/math-emu/fpu_system.h +++ b/arch/x86/math-emu/fpu_system.h | |||
@@ -104,7 +104,7 @@ static inline bool seg_writable(struct desc_struct *d) | |||
104 | #define instruction_address (*(struct address *)&I387->soft.fip) | 104 | #define instruction_address (*(struct address *)&I387->soft.fip) |
105 | #define operand_address (*(struct address *)&I387->soft.foo) | 105 | #define operand_address (*(struct address *)&I387->soft.foo) |
106 | 106 | ||
107 | #define FPU_access_ok(x,y,z) if ( !access_ok(x,y,z) ) \ | 107 | #define FPU_access_ok(y,z) if ( !access_ok(y,z) ) \ |
108 | math_abort(FPU_info,SIGSEGV) | 108 | math_abort(FPU_info,SIGSEGV) |
109 | #define FPU_abort math_abort(FPU_info, SIGSEGV) | 109 | #define FPU_abort math_abort(FPU_info, SIGSEGV) |
110 | 110 | ||
@@ -119,7 +119,7 @@ static inline bool seg_writable(struct desc_struct *d) | |||
119 | /* A simpler test than access_ok() can probably be done for | 119 | /* A simpler test than access_ok() can probably be done for |
120 | FPU_code_access_ok() because the only possible error is to step | 120 | FPU_code_access_ok() because the only possible error is to step |
121 | past the upper boundary of a legal code area. */ | 121 | past the upper boundary of a legal code area. */ |
122 | #define FPU_code_access_ok(z) FPU_access_ok(VERIFY_READ,(void __user *)FPU_EIP,z) | 122 | #define FPU_code_access_ok(z) FPU_access_ok((void __user *)FPU_EIP,z) |
123 | #endif | 123 | #endif |
124 | 124 | ||
125 | #define FPU_get_user(x,y) get_user((x),(y)) | 125 | #define FPU_get_user(x,y) get_user((x),(y)) |
diff --git a/arch/x86/math-emu/load_store.c b/arch/x86/math-emu/load_store.c index f821a9cd7753..f15263e158e8 100644 --- a/arch/x86/math-emu/load_store.c +++ b/arch/x86/math-emu/load_store.c | |||
@@ -251,7 +251,7 @@ int FPU_load_store(u_char type, fpu_addr_modes addr_modes, | |||
251 | break; | 251 | break; |
252 | case 024: /* fldcw */ | 252 | case 024: /* fldcw */ |
253 | RE_ENTRANT_CHECK_OFF; | 253 | RE_ENTRANT_CHECK_OFF; |
254 | FPU_access_ok(VERIFY_READ, data_address, 2); | 254 | FPU_access_ok(data_address, 2); |
255 | FPU_get_user(control_word, | 255 | FPU_get_user(control_word, |
256 | (unsigned short __user *)data_address); | 256 | (unsigned short __user *)data_address); |
257 | RE_ENTRANT_CHECK_ON; | 257 | RE_ENTRANT_CHECK_ON; |
@@ -291,7 +291,7 @@ int FPU_load_store(u_char type, fpu_addr_modes addr_modes, | |||
291 | break; | 291 | break; |
292 | case 034: /* fstcw m16int */ | 292 | case 034: /* fstcw m16int */ |
293 | RE_ENTRANT_CHECK_OFF; | 293 | RE_ENTRANT_CHECK_OFF; |
294 | FPU_access_ok(VERIFY_WRITE, data_address, 2); | 294 | FPU_access_ok(data_address, 2); |
295 | FPU_put_user(control_word, | 295 | FPU_put_user(control_word, |
296 | (unsigned short __user *)data_address); | 296 | (unsigned short __user *)data_address); |
297 | RE_ENTRANT_CHECK_ON; | 297 | RE_ENTRANT_CHECK_ON; |
@@ -305,7 +305,7 @@ int FPU_load_store(u_char type, fpu_addr_modes addr_modes, | |||
305 | break; | 305 | break; |
306 | case 036: /* fstsw m2byte */ | 306 | case 036: /* fstsw m2byte */ |
307 | RE_ENTRANT_CHECK_OFF; | 307 | RE_ENTRANT_CHECK_OFF; |
308 | FPU_access_ok(VERIFY_WRITE, data_address, 2); | 308 | FPU_access_ok(data_address, 2); |
309 | FPU_put_user(status_word(), | 309 | FPU_put_user(status_word(), |
310 | (unsigned short __user *)data_address); | 310 | (unsigned short __user *)data_address); |
311 | RE_ENTRANT_CHECK_ON; | 311 | RE_ENTRANT_CHECK_ON; |
diff --git a/arch/x86/math-emu/reg_ld_str.c b/arch/x86/math-emu/reg_ld_str.c index d40ff45497b9..f3779743d15e 100644 --- a/arch/x86/math-emu/reg_ld_str.c +++ b/arch/x86/math-emu/reg_ld_str.c | |||
@@ -84,7 +84,7 @@ int FPU_load_extended(long double __user *s, int stnr) | |||
84 | FPU_REG *sti_ptr = &st(stnr); | 84 | FPU_REG *sti_ptr = &st(stnr); |
85 | 85 | ||
86 | RE_ENTRANT_CHECK_OFF; | 86 | RE_ENTRANT_CHECK_OFF; |
87 | FPU_access_ok(VERIFY_READ, s, 10); | 87 | FPU_access_ok(s, 10); |
88 | __copy_from_user(sti_ptr, s, 10); | 88 | __copy_from_user(sti_ptr, s, 10); |
89 | RE_ENTRANT_CHECK_ON; | 89 | RE_ENTRANT_CHECK_ON; |
90 | 90 | ||
@@ -98,7 +98,7 @@ int FPU_load_double(double __user *dfloat, FPU_REG *loaded_data) | |||
98 | unsigned m64, l64; | 98 | unsigned m64, l64; |
99 | 99 | ||
100 | RE_ENTRANT_CHECK_OFF; | 100 | RE_ENTRANT_CHECK_OFF; |
101 | FPU_access_ok(VERIFY_READ, dfloat, 8); | 101 | FPU_access_ok(dfloat, 8); |
102 | FPU_get_user(m64, 1 + (unsigned long __user *)dfloat); | 102 | FPU_get_user(m64, 1 + (unsigned long __user *)dfloat); |
103 | FPU_get_user(l64, (unsigned long __user *)dfloat); | 103 | FPU_get_user(l64, (unsigned long __user *)dfloat); |
104 | RE_ENTRANT_CHECK_ON; | 104 | RE_ENTRANT_CHECK_ON; |
@@ -159,7 +159,7 @@ int FPU_load_single(float __user *single, FPU_REG *loaded_data) | |||
159 | int exp, tag, negative; | 159 | int exp, tag, negative; |
160 | 160 | ||
161 | RE_ENTRANT_CHECK_OFF; | 161 | RE_ENTRANT_CHECK_OFF; |
162 | FPU_access_ok(VERIFY_READ, single, 4); | 162 | FPU_access_ok(single, 4); |
163 | FPU_get_user(m32, (unsigned long __user *)single); | 163 | FPU_get_user(m32, (unsigned long __user *)single); |
164 | RE_ENTRANT_CHECK_ON; | 164 | RE_ENTRANT_CHECK_ON; |
165 | 165 | ||
@@ -214,7 +214,7 @@ int FPU_load_int64(long long __user *_s) | |||
214 | FPU_REG *st0_ptr = &st(0); | 214 | FPU_REG *st0_ptr = &st(0); |
215 | 215 | ||
216 | RE_ENTRANT_CHECK_OFF; | 216 | RE_ENTRANT_CHECK_OFF; |
217 | FPU_access_ok(VERIFY_READ, _s, 8); | 217 | FPU_access_ok(_s, 8); |
218 | if (copy_from_user(&s, _s, 8)) | 218 | if (copy_from_user(&s, _s, 8)) |
219 | FPU_abort; | 219 | FPU_abort; |
220 | RE_ENTRANT_CHECK_ON; | 220 | RE_ENTRANT_CHECK_ON; |
@@ -243,7 +243,7 @@ int FPU_load_int32(long __user *_s, FPU_REG *loaded_data) | |||
243 | int negative; | 243 | int negative; |
244 | 244 | ||
245 | RE_ENTRANT_CHECK_OFF; | 245 | RE_ENTRANT_CHECK_OFF; |
246 | FPU_access_ok(VERIFY_READ, _s, 4); | 246 | FPU_access_ok(_s, 4); |
247 | FPU_get_user(s, _s); | 247 | FPU_get_user(s, _s); |
248 | RE_ENTRANT_CHECK_ON; | 248 | RE_ENTRANT_CHECK_ON; |
249 | 249 | ||
@@ -271,7 +271,7 @@ int FPU_load_int16(short __user *_s, FPU_REG *loaded_data) | |||
271 | int s, negative; | 271 | int s, negative; |
272 | 272 | ||
273 | RE_ENTRANT_CHECK_OFF; | 273 | RE_ENTRANT_CHECK_OFF; |
274 | FPU_access_ok(VERIFY_READ, _s, 2); | 274 | FPU_access_ok(_s, 2); |
275 | /* Cast as short to get the sign extended. */ | 275 | /* Cast as short to get the sign extended. */ |
276 | FPU_get_user(s, _s); | 276 | FPU_get_user(s, _s); |
277 | RE_ENTRANT_CHECK_ON; | 277 | RE_ENTRANT_CHECK_ON; |
@@ -304,7 +304,7 @@ int FPU_load_bcd(u_char __user *s) | |||
304 | int sign; | 304 | int sign; |
305 | 305 | ||
306 | RE_ENTRANT_CHECK_OFF; | 306 | RE_ENTRANT_CHECK_OFF; |
307 | FPU_access_ok(VERIFY_READ, s, 10); | 307 | FPU_access_ok(s, 10); |
308 | RE_ENTRANT_CHECK_ON; | 308 | RE_ENTRANT_CHECK_ON; |
309 | for (pos = 8; pos >= 0; pos--) { | 309 | for (pos = 8; pos >= 0; pos--) { |
310 | l *= 10; | 310 | l *= 10; |
@@ -345,7 +345,7 @@ int FPU_store_extended(FPU_REG *st0_ptr, u_char st0_tag, | |||
345 | 345 | ||
346 | if (st0_tag != TAG_Empty) { | 346 | if (st0_tag != TAG_Empty) { |
347 | RE_ENTRANT_CHECK_OFF; | 347 | RE_ENTRANT_CHECK_OFF; |
348 | FPU_access_ok(VERIFY_WRITE, d, 10); | 348 | FPU_access_ok(d, 10); |
349 | 349 | ||
350 | FPU_put_user(st0_ptr->sigl, (unsigned long __user *)d); | 350 | FPU_put_user(st0_ptr->sigl, (unsigned long __user *)d); |
351 | FPU_put_user(st0_ptr->sigh, | 351 | FPU_put_user(st0_ptr->sigh, |
@@ -364,7 +364,7 @@ int FPU_store_extended(FPU_REG *st0_ptr, u_char st0_tag, | |||
364 | /* The masked response */ | 364 | /* The masked response */ |
365 | /* Put out the QNaN indefinite */ | 365 | /* Put out the QNaN indefinite */ |
366 | RE_ENTRANT_CHECK_OFF; | 366 | RE_ENTRANT_CHECK_OFF; |
367 | FPU_access_ok(VERIFY_WRITE, d, 10); | 367 | FPU_access_ok(d, 10); |
368 | FPU_put_user(0, (unsigned long __user *)d); | 368 | FPU_put_user(0, (unsigned long __user *)d); |
369 | FPU_put_user(0xc0000000, 1 + (unsigned long __user *)d); | 369 | FPU_put_user(0xc0000000, 1 + (unsigned long __user *)d); |
370 | FPU_put_user(0xffff, 4 + (short __user *)d); | 370 | FPU_put_user(0xffff, 4 + (short __user *)d); |
@@ -539,7 +539,7 @@ denormal_arg: | |||
539 | /* The masked response */ | 539 | /* The masked response */ |
540 | /* Put out the QNaN indefinite */ | 540 | /* Put out the QNaN indefinite */ |
541 | RE_ENTRANT_CHECK_OFF; | 541 | RE_ENTRANT_CHECK_OFF; |
542 | FPU_access_ok(VERIFY_WRITE, dfloat, 8); | 542 | FPU_access_ok(dfloat, 8); |
543 | FPU_put_user(0, (unsigned long __user *)dfloat); | 543 | FPU_put_user(0, (unsigned long __user *)dfloat); |
544 | FPU_put_user(0xfff80000, | 544 | FPU_put_user(0xfff80000, |
545 | 1 + (unsigned long __user *)dfloat); | 545 | 1 + (unsigned long __user *)dfloat); |
@@ -552,7 +552,7 @@ denormal_arg: | |||
552 | l[1] |= 0x80000000; | 552 | l[1] |= 0x80000000; |
553 | 553 | ||
554 | RE_ENTRANT_CHECK_OFF; | 554 | RE_ENTRANT_CHECK_OFF; |
555 | FPU_access_ok(VERIFY_WRITE, dfloat, 8); | 555 | FPU_access_ok(dfloat, 8); |
556 | FPU_put_user(l[0], (unsigned long __user *)dfloat); | 556 | FPU_put_user(l[0], (unsigned long __user *)dfloat); |
557 | FPU_put_user(l[1], 1 + (unsigned long __user *)dfloat); | 557 | FPU_put_user(l[1], 1 + (unsigned long __user *)dfloat); |
558 | RE_ENTRANT_CHECK_ON; | 558 | RE_ENTRANT_CHECK_ON; |
@@ -724,7 +724,7 @@ int FPU_store_single(FPU_REG *st0_ptr, u_char st0_tag, float __user *single) | |||
724 | /* The masked response */ | 724 | /* The masked response */ |
725 | /* Put out the QNaN indefinite */ | 725 | /* Put out the QNaN indefinite */ |
726 | RE_ENTRANT_CHECK_OFF; | 726 | RE_ENTRANT_CHECK_OFF; |
727 | FPU_access_ok(VERIFY_WRITE, single, 4); | 727 | FPU_access_ok(single, 4); |
728 | FPU_put_user(0xffc00000, | 728 | FPU_put_user(0xffc00000, |
729 | (unsigned long __user *)single); | 729 | (unsigned long __user *)single); |
730 | RE_ENTRANT_CHECK_ON; | 730 | RE_ENTRANT_CHECK_ON; |
@@ -742,7 +742,7 @@ int FPU_store_single(FPU_REG *st0_ptr, u_char st0_tag, float __user *single) | |||
742 | templ |= 0x80000000; | 742 | templ |= 0x80000000; |
743 | 743 | ||
744 | RE_ENTRANT_CHECK_OFF; | 744 | RE_ENTRANT_CHECK_OFF; |
745 | FPU_access_ok(VERIFY_WRITE, single, 4); | 745 | FPU_access_ok(single, 4); |
746 | FPU_put_user(templ, (unsigned long __user *)single); | 746 | FPU_put_user(templ, (unsigned long __user *)single); |
747 | RE_ENTRANT_CHECK_ON; | 747 | RE_ENTRANT_CHECK_ON; |
748 | 748 | ||
@@ -791,7 +791,7 @@ int FPU_store_int64(FPU_REG *st0_ptr, u_char st0_tag, long long __user *d) | |||
791 | } | 791 | } |
792 | 792 | ||
793 | RE_ENTRANT_CHECK_OFF; | 793 | RE_ENTRANT_CHECK_OFF; |
794 | FPU_access_ok(VERIFY_WRITE, d, 8); | 794 | FPU_access_ok(d, 8); |
795 | if (copy_to_user(d, &tll, 8)) | 795 | if (copy_to_user(d, &tll, 8)) |
796 | FPU_abort; | 796 | FPU_abort; |
797 | RE_ENTRANT_CHECK_ON; | 797 | RE_ENTRANT_CHECK_ON; |
@@ -838,7 +838,7 @@ int FPU_store_int32(FPU_REG *st0_ptr, u_char st0_tag, long __user *d) | |||
838 | } | 838 | } |
839 | 839 | ||
840 | RE_ENTRANT_CHECK_OFF; | 840 | RE_ENTRANT_CHECK_OFF; |
841 | FPU_access_ok(VERIFY_WRITE, d, 4); | 841 | FPU_access_ok(d, 4); |
842 | FPU_put_user(t.sigl, (unsigned long __user *)d); | 842 | FPU_put_user(t.sigl, (unsigned long __user *)d); |
843 | RE_ENTRANT_CHECK_ON; | 843 | RE_ENTRANT_CHECK_ON; |
844 | 844 | ||
@@ -884,7 +884,7 @@ int FPU_store_int16(FPU_REG *st0_ptr, u_char st0_tag, short __user *d) | |||
884 | } | 884 | } |
885 | 885 | ||
886 | RE_ENTRANT_CHECK_OFF; | 886 | RE_ENTRANT_CHECK_OFF; |
887 | FPU_access_ok(VERIFY_WRITE, d, 2); | 887 | FPU_access_ok(d, 2); |
888 | FPU_put_user((short)t.sigl, d); | 888 | FPU_put_user((short)t.sigl, d); |
889 | RE_ENTRANT_CHECK_ON; | 889 | RE_ENTRANT_CHECK_ON; |
890 | 890 | ||
@@ -925,7 +925,7 @@ int FPU_store_bcd(FPU_REG *st0_ptr, u_char st0_tag, u_char __user *d) | |||
925 | if (control_word & CW_Invalid) { | 925 | if (control_word & CW_Invalid) { |
926 | /* Produce the QNaN "indefinite" */ | 926 | /* Produce the QNaN "indefinite" */ |
927 | RE_ENTRANT_CHECK_OFF; | 927 | RE_ENTRANT_CHECK_OFF; |
928 | FPU_access_ok(VERIFY_WRITE, d, 10); | 928 | FPU_access_ok(d, 10); |
929 | for (i = 0; i < 7; i++) | 929 | for (i = 0; i < 7; i++) |
930 | FPU_put_user(0, d + i); /* These bytes "undefined" */ | 930 | FPU_put_user(0, d + i); /* These bytes "undefined" */ |
931 | FPU_put_user(0xc0, d + 7); /* This byte "undefined" */ | 931 | FPU_put_user(0xc0, d + 7); /* This byte "undefined" */ |
@@ -941,7 +941,7 @@ int FPU_store_bcd(FPU_REG *st0_ptr, u_char st0_tag, u_char __user *d) | |||
941 | } | 941 | } |
942 | 942 | ||
943 | RE_ENTRANT_CHECK_OFF; | 943 | RE_ENTRANT_CHECK_OFF; |
944 | FPU_access_ok(VERIFY_WRITE, d, 10); | 944 | FPU_access_ok(d, 10); |
945 | RE_ENTRANT_CHECK_ON; | 945 | RE_ENTRANT_CHECK_ON; |
946 | for (i = 0; i < 9; i++) { | 946 | for (i = 0; i < 9; i++) { |
947 | b = FPU_div_small(&ll, 10); | 947 | b = FPU_div_small(&ll, 10); |
@@ -1034,7 +1034,7 @@ u_char __user *fldenv(fpu_addr_modes addr_modes, u_char __user *s) | |||
1034 | ((addr_modes.default_mode == PM16) | 1034 | ((addr_modes.default_mode == PM16) |
1035 | ^ (addr_modes.override.operand_size == OP_SIZE_PREFIX))) { | 1035 | ^ (addr_modes.override.operand_size == OP_SIZE_PREFIX))) { |
1036 | RE_ENTRANT_CHECK_OFF; | 1036 | RE_ENTRANT_CHECK_OFF; |
1037 | FPU_access_ok(VERIFY_READ, s, 0x0e); | 1037 | FPU_access_ok(s, 0x0e); |
1038 | FPU_get_user(control_word, (unsigned short __user *)s); | 1038 | FPU_get_user(control_word, (unsigned short __user *)s); |
1039 | FPU_get_user(partial_status, (unsigned short __user *)(s + 2)); | 1039 | FPU_get_user(partial_status, (unsigned short __user *)(s + 2)); |
1040 | FPU_get_user(tag_word, (unsigned short __user *)(s + 4)); | 1040 | FPU_get_user(tag_word, (unsigned short __user *)(s + 4)); |
@@ -1056,7 +1056,7 @@ u_char __user *fldenv(fpu_addr_modes addr_modes, u_char __user *s) | |||
1056 | } | 1056 | } |
1057 | } else { | 1057 | } else { |
1058 | RE_ENTRANT_CHECK_OFF; | 1058 | RE_ENTRANT_CHECK_OFF; |
1059 | FPU_access_ok(VERIFY_READ, s, 0x1c); | 1059 | FPU_access_ok(s, 0x1c); |
1060 | FPU_get_user(control_word, (unsigned short __user *)s); | 1060 | FPU_get_user(control_word, (unsigned short __user *)s); |
1061 | FPU_get_user(partial_status, (unsigned short __user *)(s + 4)); | 1061 | FPU_get_user(partial_status, (unsigned short __user *)(s + 4)); |
1062 | FPU_get_user(tag_word, (unsigned short __user *)(s + 8)); | 1062 | FPU_get_user(tag_word, (unsigned short __user *)(s + 8)); |
@@ -1125,7 +1125,7 @@ void frstor(fpu_addr_modes addr_modes, u_char __user *data_address) | |||
1125 | 1125 | ||
1126 | /* Copy all registers in stack order. */ | 1126 | /* Copy all registers in stack order. */ |
1127 | RE_ENTRANT_CHECK_OFF; | 1127 | RE_ENTRANT_CHECK_OFF; |
1128 | FPU_access_ok(VERIFY_READ, s, 80); | 1128 | FPU_access_ok(s, 80); |
1129 | __copy_from_user(register_base + offset, s, other); | 1129 | __copy_from_user(register_base + offset, s, other); |
1130 | if (offset) | 1130 | if (offset) |
1131 | __copy_from_user(register_base, s + other, offset); | 1131 | __copy_from_user(register_base, s + other, offset); |
@@ -1146,7 +1146,7 @@ u_char __user *fstenv(fpu_addr_modes addr_modes, u_char __user *d) | |||
1146 | ((addr_modes.default_mode == PM16) | 1146 | ((addr_modes.default_mode == PM16) |
1147 | ^ (addr_modes.override.operand_size == OP_SIZE_PREFIX))) { | 1147 | ^ (addr_modes.override.operand_size == OP_SIZE_PREFIX))) { |
1148 | RE_ENTRANT_CHECK_OFF; | 1148 | RE_ENTRANT_CHECK_OFF; |
1149 | FPU_access_ok(VERIFY_WRITE, d, 14); | 1149 | FPU_access_ok(d, 14); |
1150 | #ifdef PECULIAR_486 | 1150 | #ifdef PECULIAR_486 |
1151 | FPU_put_user(control_word & ~0xe080, (unsigned long __user *)d); | 1151 | FPU_put_user(control_word & ~0xe080, (unsigned long __user *)d); |
1152 | #else | 1152 | #else |
@@ -1174,7 +1174,7 @@ u_char __user *fstenv(fpu_addr_modes addr_modes, u_char __user *d) | |||
1174 | d += 0x0e; | 1174 | d += 0x0e; |
1175 | } else { | 1175 | } else { |
1176 | RE_ENTRANT_CHECK_OFF; | 1176 | RE_ENTRANT_CHECK_OFF; |
1177 | FPU_access_ok(VERIFY_WRITE, d, 7 * 4); | 1177 | FPU_access_ok(d, 7 * 4); |
1178 | #ifdef PECULIAR_486 | 1178 | #ifdef PECULIAR_486 |
1179 | control_word &= ~0xe080; | 1179 | control_word &= ~0xe080; |
1180 | /* An 80486 sets nearly all of the reserved bits to 1. */ | 1180 | /* An 80486 sets nearly all of the reserved bits to 1. */ |
@@ -1204,7 +1204,7 @@ void fsave(fpu_addr_modes addr_modes, u_char __user *data_address) | |||
1204 | d = fstenv(addr_modes, data_address); | 1204 | d = fstenv(addr_modes, data_address); |
1205 | 1205 | ||
1206 | RE_ENTRANT_CHECK_OFF; | 1206 | RE_ENTRANT_CHECK_OFF; |
1207 | FPU_access_ok(VERIFY_WRITE, d, 80); | 1207 | FPU_access_ok(d, 80); |
1208 | 1208 | ||
1209 | /* Copy all registers in stack order. */ | 1209 | /* Copy all registers in stack order. */ |
1210 | if (__copy_to_user(d, register_base + offset, other)) | 1210 | if (__copy_to_user(d, register_base + offset, other)) |
diff --git a/arch/x86/mm/mpx.c b/arch/x86/mm/mpx.c index 2385538e8065..de1851d15699 100644 --- a/arch/x86/mm/mpx.c +++ b/arch/x86/mm/mpx.c | |||
@@ -495,7 +495,7 @@ static int get_bt_addr(struct mm_struct *mm, | |||
495 | unsigned long bd_entry; | 495 | unsigned long bd_entry; |
496 | unsigned long bt_addr; | 496 | unsigned long bt_addr; |
497 | 497 | ||
498 | if (!access_ok(VERIFY_READ, (bd_entry_ptr), sizeof(*bd_entry_ptr))) | 498 | if (!access_ok((bd_entry_ptr), sizeof(*bd_entry_ptr))) |
499 | return -EFAULT; | 499 | return -EFAULT; |
500 | 500 | ||
501 | while (1) { | 501 | while (1) { |
diff --git a/arch/x86/um/asm/checksum_32.h b/arch/x86/um/asm/checksum_32.h index 83a75f8a1233..b9ac7c9eb72c 100644 --- a/arch/x86/um/asm/checksum_32.h +++ b/arch/x86/um/asm/checksum_32.h | |||
@@ -43,7 +43,7 @@ static __inline__ __wsum csum_and_copy_to_user(const void *src, | |||
43 | void __user *dst, | 43 | void __user *dst, |
44 | int len, __wsum sum, int *err_ptr) | 44 | int len, __wsum sum, int *err_ptr) |
45 | { | 45 | { |
46 | if (access_ok(VERIFY_WRITE, dst, len)) { | 46 | if (access_ok(dst, len)) { |
47 | if (copy_to_user(dst, src, len)) { | 47 | if (copy_to_user(dst, src, len)) { |
48 | *err_ptr = -EFAULT; | 48 | *err_ptr = -EFAULT; |
49 | return (__force __wsum)-1; | 49 | return (__force __wsum)-1; |
diff --git a/arch/x86/um/signal.c b/arch/x86/um/signal.c index 727ed442e0a5..8b4a71efe7ee 100644 --- a/arch/x86/um/signal.c +++ b/arch/x86/um/signal.c | |||
@@ -367,7 +367,7 @@ int setup_signal_stack_sc(unsigned long stack_top, struct ksignal *ksig, | |||
367 | /* This is the same calculation as i386 - ((sp + 4) & 15) == 0 */ | 367 | /* This is the same calculation as i386 - ((sp + 4) & 15) == 0 */ |
368 | stack_top = ((stack_top + 4) & -16UL) - 4; | 368 | stack_top = ((stack_top + 4) & -16UL) - 4; |
369 | frame = (struct sigframe __user *) stack_top - 1; | 369 | frame = (struct sigframe __user *) stack_top - 1; |
370 | if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame))) | 370 | if (!access_ok(frame, sizeof(*frame))) |
371 | return 1; | 371 | return 1; |
372 | 372 | ||
373 | restorer = frame->retcode; | 373 | restorer = frame->retcode; |
@@ -412,7 +412,7 @@ int setup_signal_stack_si(unsigned long stack_top, struct ksignal *ksig, | |||
412 | 412 | ||
413 | stack_top &= -8UL; | 413 | stack_top &= -8UL; |
414 | frame = (struct rt_sigframe __user *) stack_top - 1; | 414 | frame = (struct rt_sigframe __user *) stack_top - 1; |
415 | if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame))) | 415 | if (!access_ok(frame, sizeof(*frame))) |
416 | return 1; | 416 | return 1; |
417 | 417 | ||
418 | restorer = frame->retcode; | 418 | restorer = frame->retcode; |
@@ -497,7 +497,7 @@ int setup_signal_stack_si(unsigned long stack_top, struct ksignal *ksig, | |||
497 | /* Subtract 128 for a red zone and 8 for proper alignment */ | 497 | /* Subtract 128 for a red zone and 8 for proper alignment */ |
498 | frame = (struct rt_sigframe __user *) ((unsigned long) frame - 128 - 8); | 498 | frame = (struct rt_sigframe __user *) ((unsigned long) frame - 128 - 8); |
499 | 499 | ||
500 | if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame))) | 500 | if (!access_ok(frame, sizeof(*frame))) |
501 | goto out; | 501 | goto out; |
502 | 502 | ||
503 | if (ksig->ka.sa.sa_flags & SA_SIGINFO) { | 503 | if (ksig->ka.sa.sa_flags & SA_SIGINFO) { |
diff --git a/arch/xtensa/include/asm/checksum.h b/arch/xtensa/include/asm/checksum.h index 3ae74d7e074b..f302ef57973a 100644 --- a/arch/xtensa/include/asm/checksum.h +++ b/arch/xtensa/include/asm/checksum.h | |||
@@ -243,7 +243,7 @@ static __inline__ __wsum csum_and_copy_to_user(const void *src, | |||
243 | void __user *dst, int len, | 243 | void __user *dst, int len, |
244 | __wsum sum, int *err_ptr) | 244 | __wsum sum, int *err_ptr) |
245 | { | 245 | { |
246 | if (access_ok(VERIFY_WRITE, dst, len)) | 246 | if (access_ok(dst, len)) |
247 | return csum_partial_copy_generic(src,dst,len,sum,NULL,err_ptr); | 247 | return csum_partial_copy_generic(src,dst,len,sum,NULL,err_ptr); |
248 | 248 | ||
249 | if (len) | 249 | if (len) |
diff --git a/arch/xtensa/include/asm/futex.h b/arch/xtensa/include/asm/futex.h index fd0eef6b8e7c..505d09eff184 100644 --- a/arch/xtensa/include/asm/futex.h +++ b/arch/xtensa/include/asm/futex.h | |||
@@ -93,7 +93,7 @@ futex_atomic_cmpxchg_inatomic(u32 *uval, u32 __user *uaddr, | |||
93 | { | 93 | { |
94 | int ret = 0; | 94 | int ret = 0; |
95 | 95 | ||
96 | if (!access_ok(VERIFY_WRITE, uaddr, sizeof(u32))) | 96 | if (!access_ok(uaddr, sizeof(u32))) |
97 | return -EFAULT; | 97 | return -EFAULT; |
98 | 98 | ||
99 | #if !XCHAL_HAVE_S32C1I | 99 | #if !XCHAL_HAVE_S32C1I |
diff --git a/arch/xtensa/include/asm/uaccess.h b/arch/xtensa/include/asm/uaccess.h index d11ef2939652..4b2480304bc3 100644 --- a/arch/xtensa/include/asm/uaccess.h +++ b/arch/xtensa/include/asm/uaccess.h | |||
@@ -42,7 +42,7 @@ | |||
42 | #define __user_ok(addr, size) \ | 42 | #define __user_ok(addr, size) \ |
43 | (((size) <= TASK_SIZE)&&((addr) <= TASK_SIZE-(size))) | 43 | (((size) <= TASK_SIZE)&&((addr) <= TASK_SIZE-(size))) |
44 | #define __access_ok(addr, size) (__kernel_ok || __user_ok((addr), (size))) | 44 | #define __access_ok(addr, size) (__kernel_ok || __user_ok((addr), (size))) |
45 | #define access_ok(type, addr, size) __access_ok((unsigned long)(addr), (size)) | 45 | #define access_ok(addr, size) __access_ok((unsigned long)(addr), (size)) |
46 | 46 | ||
47 | #define user_addr_max() (uaccess_kernel() ? ~0UL : TASK_SIZE) | 47 | #define user_addr_max() (uaccess_kernel() ? ~0UL : TASK_SIZE) |
48 | 48 | ||
@@ -86,7 +86,7 @@ extern long __put_user_bad(void); | |||
86 | ({ \ | 86 | ({ \ |
87 | long __pu_err = -EFAULT; \ | 87 | long __pu_err = -EFAULT; \ |
88 | __typeof__(*(ptr)) *__pu_addr = (ptr); \ | 88 | __typeof__(*(ptr)) *__pu_addr = (ptr); \ |
89 | if (access_ok(VERIFY_WRITE, __pu_addr, size)) \ | 89 | if (access_ok(__pu_addr, size)) \ |
90 | __put_user_size((x), __pu_addr, (size), __pu_err); \ | 90 | __put_user_size((x), __pu_addr, (size), __pu_err); \ |
91 | __pu_err; \ | 91 | __pu_err; \ |
92 | }) | 92 | }) |
@@ -183,7 +183,7 @@ __asm__ __volatile__( \ | |||
183 | ({ \ | 183 | ({ \ |
184 | long __gu_err = -EFAULT, __gu_val = 0; \ | 184 | long __gu_err = -EFAULT, __gu_val = 0; \ |
185 | const __typeof__(*(ptr)) *__gu_addr = (ptr); \ | 185 | const __typeof__(*(ptr)) *__gu_addr = (ptr); \ |
186 | if (access_ok(VERIFY_READ, __gu_addr, size)) \ | 186 | if (access_ok(__gu_addr, size)) \ |
187 | __get_user_size(__gu_val, __gu_addr, (size), __gu_err); \ | 187 | __get_user_size(__gu_val, __gu_addr, (size), __gu_err); \ |
188 | (x) = (__force __typeof__(*(ptr)))__gu_val; \ | 188 | (x) = (__force __typeof__(*(ptr)))__gu_val; \ |
189 | __gu_err; \ | 189 | __gu_err; \ |
@@ -269,7 +269,7 @@ __xtensa_clear_user(void *addr, unsigned long size) | |||
269 | static inline unsigned long | 269 | static inline unsigned long |
270 | clear_user(void *addr, unsigned long size) | 270 | clear_user(void *addr, unsigned long size) |
271 | { | 271 | { |
272 | if (access_ok(VERIFY_WRITE, addr, size)) | 272 | if (access_ok(addr, size)) |
273 | return __xtensa_clear_user(addr, size); | 273 | return __xtensa_clear_user(addr, size); |
274 | return size ? -EFAULT : 0; | 274 | return size ? -EFAULT : 0; |
275 | } | 275 | } |
@@ -284,7 +284,7 @@ extern long __strncpy_user(char *, const char *, long); | |||
284 | static inline long | 284 | static inline long |
285 | strncpy_from_user(char *dst, const char *src, long count) | 285 | strncpy_from_user(char *dst, const char *src, long count) |
286 | { | 286 | { |
287 | if (access_ok(VERIFY_READ, src, 1)) | 287 | if (access_ok(src, 1)) |
288 | return __strncpy_user(dst, src, count); | 288 | return __strncpy_user(dst, src, count); |
289 | return -EFAULT; | 289 | return -EFAULT; |
290 | } | 290 | } |
diff --git a/arch/xtensa/kernel/signal.c b/arch/xtensa/kernel/signal.c index 74e1682876ac..dc22a238ed9c 100644 --- a/arch/xtensa/kernel/signal.c +++ b/arch/xtensa/kernel/signal.c | |||
@@ -251,7 +251,7 @@ asmlinkage long xtensa_rt_sigreturn(long a0, long a1, long a2, long a3, | |||
251 | 251 | ||
252 | frame = (struct rt_sigframe __user *) regs->areg[1]; | 252 | frame = (struct rt_sigframe __user *) regs->areg[1]; |
253 | 253 | ||
254 | if (!access_ok(VERIFY_READ, frame, sizeof(*frame))) | 254 | if (!access_ok(frame, sizeof(*frame))) |
255 | goto badframe; | 255 | goto badframe; |
256 | 256 | ||
257 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) | 257 | if (__copy_from_user(&set, &frame->uc.uc_sigmask, sizeof(set))) |
@@ -348,7 +348,7 @@ static int setup_frame(struct ksignal *ksig, sigset_t *set, | |||
348 | if (regs->depc > 64) | 348 | if (regs->depc > 64) |
349 | panic ("Double exception sys_sigreturn\n"); | 349 | panic ("Double exception sys_sigreturn\n"); |
350 | 350 | ||
351 | if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame))) { | 351 | if (!access_ok(frame, sizeof(*frame))) { |
352 | return -EFAULT; | 352 | return -EFAULT; |
353 | } | 353 | } |
354 | 354 | ||
diff --git a/arch/xtensa/kernel/stacktrace.c b/arch/xtensa/kernel/stacktrace.c index 0df4080fa20f..174c11f13bba 100644 --- a/arch/xtensa/kernel/stacktrace.c +++ b/arch/xtensa/kernel/stacktrace.c | |||
@@ -91,7 +91,7 @@ void xtensa_backtrace_user(struct pt_regs *regs, unsigned int depth, | |||
91 | pc = MAKE_PC_FROM_RA(a0, pc); | 91 | pc = MAKE_PC_FROM_RA(a0, pc); |
92 | 92 | ||
93 | /* Check if the region is OK to access. */ | 93 | /* Check if the region is OK to access. */ |
94 | if (!access_ok(VERIFY_READ, &SPILL_SLOT(a1, 0), 8)) | 94 | if (!access_ok(&SPILL_SLOT(a1, 0), 8)) |
95 | return; | 95 | return; |
96 | /* Copy a1, a0 from user space stack frame. */ | 96 | /* Copy a1, a0 from user space stack frame. */ |
97 | if (__get_user(a0, &SPILL_SLOT(a1, 0)) || | 97 | if (__get_user(a0, &SPILL_SLOT(a1, 0)) || |
diff --git a/drivers/acpi/acpi_dbg.c b/drivers/acpi/acpi_dbg.c index f21c99ec46ee..a2dcd62ea32f 100644 --- a/drivers/acpi/acpi_dbg.c +++ b/drivers/acpi/acpi_dbg.c | |||
@@ -614,7 +614,7 @@ static ssize_t acpi_aml_read(struct file *file, char __user *buf, | |||
614 | 614 | ||
615 | if (!count) | 615 | if (!count) |
616 | return 0; | 616 | return 0; |
617 | if (!access_ok(VERIFY_WRITE, buf, count)) | 617 | if (!access_ok(buf, count)) |
618 | return -EFAULT; | 618 | return -EFAULT; |
619 | 619 | ||
620 | while (count > 0) { | 620 | while (count > 0) { |
@@ -684,7 +684,7 @@ static ssize_t acpi_aml_write(struct file *file, const char __user *buf, | |||
684 | 684 | ||
685 | if (!count) | 685 | if (!count) |
686 | return 0; | 686 | return 0; |
687 | if (!access_ok(VERIFY_READ, buf, count)) | 687 | if (!access_ok(buf, count)) |
688 | return -EFAULT; | 688 | return -EFAULT; |
689 | 689 | ||
690 | while (count > 0) { | 690 | while (count > 0) { |
diff --git a/drivers/char/generic_nvram.c b/drivers/char/generic_nvram.c index 14e728fbb8a0..ff5394f47587 100644 --- a/drivers/char/generic_nvram.c +++ b/drivers/char/generic_nvram.c | |||
@@ -44,7 +44,7 @@ static ssize_t read_nvram(struct file *file, char __user *buf, | |||
44 | unsigned int i; | 44 | unsigned int i; |
45 | char __user *p = buf; | 45 | char __user *p = buf; |
46 | 46 | ||
47 | if (!access_ok(VERIFY_WRITE, buf, count)) | 47 | if (!access_ok(buf, count)) |
48 | return -EFAULT; | 48 | return -EFAULT; |
49 | if (*ppos >= nvram_len) | 49 | if (*ppos >= nvram_len) |
50 | return 0; | 50 | return 0; |
@@ -62,7 +62,7 @@ static ssize_t write_nvram(struct file *file, const char __user *buf, | |||
62 | const char __user *p = buf; | 62 | const char __user *p = buf; |
63 | char c; | 63 | char c; |
64 | 64 | ||
65 | if (!access_ok(VERIFY_READ, buf, count)) | 65 | if (!access_ok(buf, count)) |
66 | return -EFAULT; | 66 | return -EFAULT; |
67 | if (*ppos >= nvram_len) | 67 | if (*ppos >= nvram_len) |
68 | return 0; | 68 | return 0; |
diff --git a/drivers/char/mem.c b/drivers/char/mem.c index 7b4e4de778e4..b08dc50f9f26 100644 --- a/drivers/char/mem.c +++ b/drivers/char/mem.c | |||
@@ -609,7 +609,7 @@ static ssize_t read_port(struct file *file, char __user *buf, | |||
609 | unsigned long i = *ppos; | 609 | unsigned long i = *ppos; |
610 | char __user *tmp = buf; | 610 | char __user *tmp = buf; |
611 | 611 | ||
612 | if (!access_ok(VERIFY_WRITE, buf, count)) | 612 | if (!access_ok(buf, count)) |
613 | return -EFAULT; | 613 | return -EFAULT; |
614 | while (count-- > 0 && i < 65536) { | 614 | while (count-- > 0 && i < 65536) { |
615 | if (__put_user(inb(i), tmp) < 0) | 615 | if (__put_user(inb(i), tmp) < 0) |
@@ -627,7 +627,7 @@ static ssize_t write_port(struct file *file, const char __user *buf, | |||
627 | unsigned long i = *ppos; | 627 | unsigned long i = *ppos; |
628 | const char __user *tmp = buf; | 628 | const char __user *tmp = buf; |
629 | 629 | ||
630 | if (!access_ok(VERIFY_READ, buf, count)) | 630 | if (!access_ok(buf, count)) |
631 | return -EFAULT; | 631 | return -EFAULT; |
632 | while (count-- > 0 && i < 65536) { | 632 | while (count-- > 0 && i < 65536) { |
633 | char c; | 633 | char c; |
diff --git a/drivers/char/nwflash.c b/drivers/char/nwflash.c index a284ae25e69a..76fb434068d4 100644 --- a/drivers/char/nwflash.c +++ b/drivers/char/nwflash.c | |||
@@ -167,7 +167,7 @@ static ssize_t flash_write(struct file *file, const char __user *buf, | |||
167 | if (count > gbFlashSize - p) | 167 | if (count > gbFlashSize - p) |
168 | count = gbFlashSize - p; | 168 | count = gbFlashSize - p; |
169 | 169 | ||
170 | if (!access_ok(VERIFY_READ, buf, count)) | 170 | if (!access_ok(buf, count)) |
171 | return -EFAULT; | 171 | return -EFAULT; |
172 | 172 | ||
173 | /* | 173 | /* |
diff --git a/drivers/char/pcmcia/cm4000_cs.c b/drivers/char/pcmcia/cm4000_cs.c index 809507bf8f1c..7a4eb86aedac 100644 --- a/drivers/char/pcmcia/cm4000_cs.c +++ b/drivers/char/pcmcia/cm4000_cs.c | |||
@@ -1445,11 +1445,11 @@ static long cmm_ioctl(struct file *filp, unsigned int cmd, unsigned long arg) | |||
1445 | _IOC_DIR(cmd), _IOC_READ, _IOC_WRITE, size, cmd); | 1445 | _IOC_DIR(cmd), _IOC_READ, _IOC_WRITE, size, cmd); |
1446 | 1446 | ||
1447 | if (_IOC_DIR(cmd) & _IOC_READ) { | 1447 | if (_IOC_DIR(cmd) & _IOC_READ) { |
1448 | if (!access_ok(VERIFY_WRITE, argp, size)) | 1448 | if (!access_ok(argp, size)) |
1449 | goto out; | 1449 | goto out; |
1450 | } | 1450 | } |
1451 | if (_IOC_DIR(cmd) & _IOC_WRITE) { | 1451 | if (_IOC_DIR(cmd) & _IOC_WRITE) { |
1452 | if (!access_ok(VERIFY_READ, argp, size)) | 1452 | if (!access_ok(argp, size)) |
1453 | goto out; | 1453 | goto out; |
1454 | } | 1454 | } |
1455 | rc = 0; | 1455 | rc = 0; |
diff --git a/drivers/crypto/ccp/psp-dev.c b/drivers/crypto/ccp/psp-dev.c index d64a78ccc03e..b16be8a11d92 100644 --- a/drivers/crypto/ccp/psp-dev.c +++ b/drivers/crypto/ccp/psp-dev.c | |||
@@ -364,7 +364,7 @@ static int sev_ioctl_do_pek_csr(struct sev_issue_cmd *argp) | |||
364 | goto cmd; | 364 | goto cmd; |
365 | 365 | ||
366 | /* allocate a physically contiguous buffer to store the CSR blob */ | 366 | /* allocate a physically contiguous buffer to store the CSR blob */ |
367 | if (!access_ok(VERIFY_WRITE, input.address, input.length) || | 367 | if (!access_ok(input.address, input.length) || |
368 | input.length > SEV_FW_BLOB_MAX_SIZE) { | 368 | input.length > SEV_FW_BLOB_MAX_SIZE) { |
369 | ret = -EFAULT; | 369 | ret = -EFAULT; |
370 | goto e_free; | 370 | goto e_free; |
@@ -644,14 +644,14 @@ static int sev_ioctl_do_pdh_export(struct sev_issue_cmd *argp) | |||
644 | 644 | ||
645 | /* Allocate a physically contiguous buffer to store the PDH blob. */ | 645 | /* Allocate a physically contiguous buffer to store the PDH blob. */ |
646 | if ((input.pdh_cert_len > SEV_FW_BLOB_MAX_SIZE) || | 646 | if ((input.pdh_cert_len > SEV_FW_BLOB_MAX_SIZE) || |
647 | !access_ok(VERIFY_WRITE, input.pdh_cert_address, input.pdh_cert_len)) { | 647 | !access_ok(input.pdh_cert_address, input.pdh_cert_len)) { |
648 | ret = -EFAULT; | 648 | ret = -EFAULT; |
649 | goto e_free; | 649 | goto e_free; |
650 | } | 650 | } |
651 | 651 | ||
652 | /* Allocate a physically contiguous buffer to store the cert chain blob. */ | 652 | /* Allocate a physically contiguous buffer to store the cert chain blob. */ |
653 | if ((input.cert_chain_len > SEV_FW_BLOB_MAX_SIZE) || | 653 | if ((input.cert_chain_len > SEV_FW_BLOB_MAX_SIZE) || |
654 | !access_ok(VERIFY_WRITE, input.cert_chain_address, input.cert_chain_len)) { | 654 | !access_ok(input.cert_chain_address, input.cert_chain_len)) { |
655 | ret = -EFAULT; | 655 | ret = -EFAULT; |
656 | goto e_free; | 656 | goto e_free; |
657 | } | 657 | } |
diff --git a/drivers/firewire/core-cdev.c b/drivers/firewire/core-cdev.c index d8e185582642..16a7045736a9 100644 --- a/drivers/firewire/core-cdev.c +++ b/drivers/firewire/core-cdev.c | |||
@@ -1094,7 +1094,7 @@ static int ioctl_queue_iso(struct client *client, union ioctl_arg *arg) | |||
1094 | return -EINVAL; | 1094 | return -EINVAL; |
1095 | 1095 | ||
1096 | p = (struct fw_cdev_iso_packet __user *)u64_to_uptr(a->packets); | 1096 | p = (struct fw_cdev_iso_packet __user *)u64_to_uptr(a->packets); |
1097 | if (!access_ok(VERIFY_READ, p, a->size)) | 1097 | if (!access_ok(p, a->size)) |
1098 | return -EFAULT; | 1098 | return -EFAULT; |
1099 | 1099 | ||
1100 | end = (void __user *)p + a->size; | 1100 | end = (void __user *)p + a->size; |
diff --git a/drivers/firmware/efi/test/efi_test.c b/drivers/firmware/efi/test/efi_test.c index 769640940c9f..51ecf7d6da48 100644 --- a/drivers/firmware/efi/test/efi_test.c +++ b/drivers/firmware/efi/test/efi_test.c | |||
@@ -68,7 +68,7 @@ copy_ucs2_from_user_len(efi_char16_t **dst, efi_char16_t __user *src, | |||
68 | return 0; | 68 | return 0; |
69 | } | 69 | } |
70 | 70 | ||
71 | if (!access_ok(VERIFY_READ, src, 1)) | 71 | if (!access_ok(src, 1)) |
72 | return -EFAULT; | 72 | return -EFAULT; |
73 | 73 | ||
74 | buf = memdup_user(src, len); | 74 | buf = memdup_user(src, len); |
@@ -89,7 +89,7 @@ copy_ucs2_from_user_len(efi_char16_t **dst, efi_char16_t __user *src, | |||
89 | static inline int | 89 | static inline int |
90 | get_ucs2_strsize_from_user(efi_char16_t __user *src, size_t *len) | 90 | get_ucs2_strsize_from_user(efi_char16_t __user *src, size_t *len) |
91 | { | 91 | { |
92 | if (!access_ok(VERIFY_READ, src, 1)) | 92 | if (!access_ok(src, 1)) |
93 | return -EFAULT; | 93 | return -EFAULT; |
94 | 94 | ||
95 | *len = user_ucs2_strsize(src); | 95 | *len = user_ucs2_strsize(src); |
@@ -116,7 +116,7 @@ copy_ucs2_from_user(efi_char16_t **dst, efi_char16_t __user *src) | |||
116 | { | 116 | { |
117 | size_t len; | 117 | size_t len; |
118 | 118 | ||
119 | if (!access_ok(VERIFY_READ, src, 1)) | 119 | if (!access_ok(src, 1)) |
120 | return -EFAULT; | 120 | return -EFAULT; |
121 | 121 | ||
122 | len = user_ucs2_strsize(src); | 122 | len = user_ucs2_strsize(src); |
@@ -140,7 +140,7 @@ copy_ucs2_to_user_len(efi_char16_t __user *dst, efi_char16_t *src, size_t len) | |||
140 | if (!src) | 140 | if (!src) |
141 | return 0; | 141 | return 0; |
142 | 142 | ||
143 | if (!access_ok(VERIFY_WRITE, dst, 1)) | 143 | if (!access_ok(dst, 1)) |
144 | return -EFAULT; | 144 | return -EFAULT; |
145 | 145 | ||
146 | return copy_to_user(dst, src, len); | 146 | return copy_to_user(dst, src, len); |
diff --git a/drivers/fpga/dfl-afu-dma-region.c b/drivers/fpga/dfl-afu-dma-region.c index 025aba3ea76c..e18a786fc943 100644 --- a/drivers/fpga/dfl-afu-dma-region.c +++ b/drivers/fpga/dfl-afu-dma-region.c | |||
@@ -369,7 +369,7 @@ int afu_dma_map_region(struct dfl_feature_platform_data *pdata, | |||
369 | if (user_addr + length < user_addr) | 369 | if (user_addr + length < user_addr) |
370 | return -EINVAL; | 370 | return -EINVAL; |
371 | 371 | ||
372 | if (!access_ok(VERIFY_WRITE, (void __user *)(unsigned long)user_addr, | 372 | if (!access_ok((void __user *)(unsigned long)user_addr, |
373 | length)) | 373 | length)) |
374 | return -EINVAL; | 374 | return -EINVAL; |
375 | 375 | ||
diff --git a/drivers/fpga/dfl-fme-pr.c b/drivers/fpga/dfl-fme-pr.c index fe5a5578fbf7..d9ca9554844a 100644 --- a/drivers/fpga/dfl-fme-pr.c +++ b/drivers/fpga/dfl-fme-pr.c | |||
@@ -99,8 +99,7 @@ static int fme_pr(struct platform_device *pdev, unsigned long arg) | |||
99 | return -EINVAL; | 99 | return -EINVAL; |
100 | } | 100 | } |
101 | 101 | ||
102 | if (!access_ok(VERIFY_READ, | 102 | if (!access_ok((void __user *)(unsigned long)port_pr.buffer_address, |
103 | (void __user *)(unsigned long)port_pr.buffer_address, | ||
104 | port_pr.buffer_size)) | 103 | port_pr.buffer_size)) |
105 | return -EFAULT; | 104 | return -EFAULT; |
106 | 105 | ||
diff --git a/drivers/gpu/drm/amd/amdkfd/kfd_chardev.c b/drivers/gpu/drm/amd/amdkfd/kfd_chardev.c index 3623538baf6f..be68752c3469 100644 --- a/drivers/gpu/drm/amd/amdkfd/kfd_chardev.c +++ b/drivers/gpu/drm/amd/amdkfd/kfd_chardev.c | |||
@@ -158,8 +158,7 @@ static int set_queue_properties_from_user(struct queue_properties *q_properties, | |||
158 | } | 158 | } |
159 | 159 | ||
160 | if ((args->ring_base_address) && | 160 | if ((args->ring_base_address) && |
161 | (!access_ok(VERIFY_WRITE, | 161 | (!access_ok((const void __user *) args->ring_base_address, |
162 | (const void __user *) args->ring_base_address, | ||
163 | sizeof(uint64_t)))) { | 162 | sizeof(uint64_t)))) { |
164 | pr_err("Can't access ring base address\n"); | 163 | pr_err("Can't access ring base address\n"); |
165 | return -EFAULT; | 164 | return -EFAULT; |
@@ -170,31 +169,27 @@ static int set_queue_properties_from_user(struct queue_properties *q_properties, | |||
170 | return -EINVAL; | 169 | return -EINVAL; |
171 | } | 170 | } |
172 | 171 | ||
173 | if (!access_ok(VERIFY_WRITE, | 172 | if (!access_ok((const void __user *) args->read_pointer_address, |
174 | (const void __user *) args->read_pointer_address, | ||
175 | sizeof(uint32_t))) { | 173 | sizeof(uint32_t))) { |
176 | pr_err("Can't access read pointer\n"); | 174 | pr_err("Can't access read pointer\n"); |
177 | return -EFAULT; | 175 | return -EFAULT; |
178 | } | 176 | } |
179 | 177 | ||
180 | if (!access_ok(VERIFY_WRITE, | 178 | if (!access_ok((const void __user *) args->write_pointer_address, |
181 | (const void __user *) args->write_pointer_address, | ||
182 | sizeof(uint32_t))) { | 179 | sizeof(uint32_t))) { |
183 | pr_err("Can't access write pointer\n"); | 180 | pr_err("Can't access write pointer\n"); |
184 | return -EFAULT; | 181 | return -EFAULT; |
185 | } | 182 | } |
186 | 183 | ||
187 | if (args->eop_buffer_address && | 184 | if (args->eop_buffer_address && |
188 | !access_ok(VERIFY_WRITE, | 185 | !access_ok((const void __user *) args->eop_buffer_address, |
189 | (const void __user *) args->eop_buffer_address, | ||
190 | sizeof(uint32_t))) { | 186 | sizeof(uint32_t))) { |
191 | pr_debug("Can't access eop buffer"); | 187 | pr_debug("Can't access eop buffer"); |
192 | return -EFAULT; | 188 | return -EFAULT; |
193 | } | 189 | } |
194 | 190 | ||
195 | if (args->ctx_save_restore_address && | 191 | if (args->ctx_save_restore_address && |
196 | !access_ok(VERIFY_WRITE, | 192 | !access_ok((const void __user *) args->ctx_save_restore_address, |
197 | (const void __user *) args->ctx_save_restore_address, | ||
198 | sizeof(uint32_t))) { | 193 | sizeof(uint32_t))) { |
199 | pr_debug("Can't access ctx save restore buffer"); | 194 | pr_debug("Can't access ctx save restore buffer"); |
200 | return -EFAULT; | 195 | return -EFAULT; |
@@ -365,8 +360,7 @@ static int kfd_ioctl_update_queue(struct file *filp, struct kfd_process *p, | |||
365 | } | 360 | } |
366 | 361 | ||
367 | if ((args->ring_base_address) && | 362 | if ((args->ring_base_address) && |
368 | (!access_ok(VERIFY_WRITE, | 363 | (!access_ok((const void __user *) args->ring_base_address, |
369 | (const void __user *) args->ring_base_address, | ||
370 | sizeof(uint64_t)))) { | 364 | sizeof(uint64_t)))) { |
371 | pr_err("Can't access ring base address\n"); | 365 | pr_err("Can't access ring base address\n"); |
372 | return -EFAULT; | 366 | return -EFAULT; |
diff --git a/drivers/gpu/drm/armada/armada_gem.c b/drivers/gpu/drm/armada/armada_gem.c index 892c1d9304bb..642d0e70d0f8 100644 --- a/drivers/gpu/drm/armada/armada_gem.c +++ b/drivers/gpu/drm/armada/armada_gem.c | |||
@@ -334,7 +334,7 @@ int armada_gem_pwrite_ioctl(struct drm_device *dev, void *data, | |||
334 | 334 | ||
335 | ptr = (char __user *)(uintptr_t)args->ptr; | 335 | ptr = (char __user *)(uintptr_t)args->ptr; |
336 | 336 | ||
337 | if (!access_ok(VERIFY_READ, ptr, args->size)) | 337 | if (!access_ok(ptr, args->size)) |
338 | return -EFAULT; | 338 | return -EFAULT; |
339 | 339 | ||
340 | ret = fault_in_pages_readable(ptr, args->size); | 340 | ret = fault_in_pages_readable(ptr, args->size); |
diff --git a/drivers/gpu/drm/drm_file.c b/drivers/gpu/drm/drm_file.c index ffa8dc35515f..46f48f245eb5 100644 --- a/drivers/gpu/drm/drm_file.c +++ b/drivers/gpu/drm/drm_file.c | |||
@@ -525,7 +525,7 @@ ssize_t drm_read(struct file *filp, char __user *buffer, | |||
525 | struct drm_device *dev = file_priv->minor->dev; | 525 | struct drm_device *dev = file_priv->minor->dev; |
526 | ssize_t ret; | 526 | ssize_t ret; |
527 | 527 | ||
528 | if (!access_ok(VERIFY_WRITE, buffer, count)) | 528 | if (!access_ok(buffer, count)) |
529 | return -EFAULT; | 529 | return -EFAULT; |
530 | 530 | ||
531 | ret = mutex_lock_interruptible(&file_priv->event_read_lock); | 531 | ret = mutex_lock_interruptible(&file_priv->event_read_lock); |
diff --git a/drivers/gpu/drm/etnaviv/etnaviv_drv.c b/drivers/gpu/drm/etnaviv/etnaviv_drv.c index 96efc84396bf..18c27f795cf6 100644 --- a/drivers/gpu/drm/etnaviv/etnaviv_drv.c +++ b/drivers/gpu/drm/etnaviv/etnaviv_drv.c | |||
@@ -339,7 +339,6 @@ static int etnaviv_ioctl_gem_userptr(struct drm_device *dev, void *data, | |||
339 | struct drm_file *file) | 339 | struct drm_file *file) |
340 | { | 340 | { |
341 | struct drm_etnaviv_gem_userptr *args = data; | 341 | struct drm_etnaviv_gem_userptr *args = data; |
342 | int access; | ||
343 | 342 | ||
344 | if (args->flags & ~(ETNA_USERPTR_READ|ETNA_USERPTR_WRITE) || | 343 | if (args->flags & ~(ETNA_USERPTR_READ|ETNA_USERPTR_WRITE) || |
345 | args->flags == 0) | 344 | args->flags == 0) |
@@ -351,12 +350,7 @@ static int etnaviv_ioctl_gem_userptr(struct drm_device *dev, void *data, | |||
351 | args->user_ptr & ~PAGE_MASK) | 350 | args->user_ptr & ~PAGE_MASK) |
352 | return -EINVAL; | 351 | return -EINVAL; |
353 | 352 | ||
354 | if (args->flags & ETNA_USERPTR_WRITE) | 353 | if (!access_ok((void __user *)(unsigned long)args->user_ptr, |
355 | access = VERIFY_WRITE; | ||
356 | else | ||
357 | access = VERIFY_READ; | ||
358 | |||
359 | if (!access_ok(access, (void __user *)(unsigned long)args->user_ptr, | ||
360 | args->user_size)) | 354 | args->user_size)) |
361 | return -EFAULT; | 355 | return -EFAULT; |
362 | 356 | ||
diff --git a/drivers/gpu/drm/i915/i915_gem.c b/drivers/gpu/drm/i915/i915_gem.c index a9de07bb72c8..216f52b744a6 100644 --- a/drivers/gpu/drm/i915/i915_gem.c +++ b/drivers/gpu/drm/i915/i915_gem.c | |||
@@ -1282,8 +1282,7 @@ i915_gem_pread_ioctl(struct drm_device *dev, void *data, | |||
1282 | if (args->size == 0) | 1282 | if (args->size == 0) |
1283 | return 0; | 1283 | return 0; |
1284 | 1284 | ||
1285 | if (!access_ok(VERIFY_WRITE, | 1285 | if (!access_ok(u64_to_user_ptr(args->data_ptr), |
1286 | u64_to_user_ptr(args->data_ptr), | ||
1287 | args->size)) | 1286 | args->size)) |
1288 | return -EFAULT; | 1287 | return -EFAULT; |
1289 | 1288 | ||
@@ -1609,9 +1608,7 @@ i915_gem_pwrite_ioctl(struct drm_device *dev, void *data, | |||
1609 | if (args->size == 0) | 1608 | if (args->size == 0) |
1610 | return 0; | 1609 | return 0; |
1611 | 1610 | ||
1612 | if (!access_ok(VERIFY_READ, | 1611 | if (!access_ok(u64_to_user_ptr(args->data_ptr), args->size)) |
1613 | u64_to_user_ptr(args->data_ptr), | ||
1614 | args->size)) | ||
1615 | return -EFAULT; | 1612 | return -EFAULT; |
1616 | 1613 | ||
1617 | obj = i915_gem_object_lookup(file, args->handle); | 1614 | obj = i915_gem_object_lookup(file, args->handle); |
diff --git a/drivers/gpu/drm/i915/i915_gem_execbuffer.c b/drivers/gpu/drm/i915/i915_gem_execbuffer.c index 8ff6b581cf1c..485b259127c3 100644 --- a/drivers/gpu/drm/i915/i915_gem_execbuffer.c +++ b/drivers/gpu/drm/i915/i915_gem_execbuffer.c | |||
@@ -1447,7 +1447,7 @@ static int eb_relocate_vma(struct i915_execbuffer *eb, struct i915_vma *vma) | |||
1447 | * to read. However, if the array is not writable the user loses | 1447 | * to read. However, if the array is not writable the user loses |
1448 | * the updated relocation values. | 1448 | * the updated relocation values. |
1449 | */ | 1449 | */ |
1450 | if (unlikely(!access_ok(VERIFY_READ, urelocs, remain*sizeof(*urelocs)))) | 1450 | if (unlikely(!access_ok(urelocs, remain*sizeof(*urelocs)))) |
1451 | return -EFAULT; | 1451 | return -EFAULT; |
1452 | 1452 | ||
1453 | do { | 1453 | do { |
@@ -1554,7 +1554,7 @@ static int check_relocations(const struct drm_i915_gem_exec_object2 *entry) | |||
1554 | 1554 | ||
1555 | addr = u64_to_user_ptr(entry->relocs_ptr); | 1555 | addr = u64_to_user_ptr(entry->relocs_ptr); |
1556 | size *= sizeof(struct drm_i915_gem_relocation_entry); | 1556 | size *= sizeof(struct drm_i915_gem_relocation_entry); |
1557 | if (!access_ok(VERIFY_READ, addr, size)) | 1557 | if (!access_ok(addr, size)) |
1558 | return -EFAULT; | 1558 | return -EFAULT; |
1559 | 1559 | ||
1560 | end = addr + size; | 1560 | end = addr + size; |
@@ -1605,6 +1605,7 @@ static int eb_copy_relocations(const struct i915_execbuffer *eb) | |||
1605 | (char __user *)urelocs + copied, | 1605 | (char __user *)urelocs + copied, |
1606 | len)) { | 1606 | len)) { |
1607 | end_user: | 1607 | end_user: |
1608 | user_access_end(); | ||
1608 | kvfree(relocs); | 1609 | kvfree(relocs); |
1609 | err = -EFAULT; | 1610 | err = -EFAULT; |
1610 | goto err; | 1611 | goto err; |
@@ -1623,7 +1624,9 @@ end_user: | |||
1623 | * happened we would make the mistake of assuming that the | 1624 | * happened we would make the mistake of assuming that the |
1624 | * relocations were valid. | 1625 | * relocations were valid. |
1625 | */ | 1626 | */ |
1626 | user_access_begin(); | 1627 | if (!user_access_begin(urelocs, size)) |
1628 | goto end_user; | ||
1629 | |||
1627 | for (copied = 0; copied < nreloc; copied++) | 1630 | for (copied = 0; copied < nreloc; copied++) |
1628 | unsafe_put_user(-1, | 1631 | unsafe_put_user(-1, |
1629 | &urelocs[copied].presumed_offset, | 1632 | &urelocs[copied].presumed_offset, |
@@ -2090,7 +2093,7 @@ get_fence_array(struct drm_i915_gem_execbuffer2 *args, | |||
2090 | return ERR_PTR(-EINVAL); | 2093 | return ERR_PTR(-EINVAL); |
2091 | 2094 | ||
2092 | user = u64_to_user_ptr(args->cliprects_ptr); | 2095 | user = u64_to_user_ptr(args->cliprects_ptr); |
2093 | if (!access_ok(VERIFY_READ, user, nfences * sizeof(*user))) | 2096 | if (!access_ok(user, nfences * sizeof(*user))) |
2094 | return ERR_PTR(-EFAULT); | 2097 | return ERR_PTR(-EFAULT); |
2095 | 2098 | ||
2096 | fences = kvmalloc_array(nfences, sizeof(*fences), | 2099 | fences = kvmalloc_array(nfences, sizeof(*fences), |
@@ -2605,7 +2608,16 @@ i915_gem_execbuffer2_ioctl(struct drm_device *dev, void *data, | |||
2605 | unsigned int i; | 2608 | unsigned int i; |
2606 | 2609 | ||
2607 | /* Copy the new buffer offsets back to the user's exec list. */ | 2610 | /* Copy the new buffer offsets back to the user's exec list. */ |
2608 | user_access_begin(); | 2611 | /* |
2612 | * Note: count * sizeof(*user_exec_list) does not overflow, | ||
2613 | * because we checked 'count' in check_buffer_count(). | ||
2614 | * | ||
2615 | * And this range already got effectively checked earlier | ||
2616 | * when we did the "copy_from_user()" above. | ||
2617 | */ | ||
2618 | if (!user_access_begin(user_exec_list, count * sizeof(*user_exec_list))) | ||
2619 | goto end_user; | ||
2620 | |||
2609 | for (i = 0; i < args->buffer_count; i++) { | 2621 | for (i = 0; i < args->buffer_count; i++) { |
2610 | if (!(exec2_list[i].offset & UPDATE)) | 2622 | if (!(exec2_list[i].offset & UPDATE)) |
2611 | continue; | 2623 | continue; |
diff --git a/drivers/gpu/drm/i915/i915_gem_userptr.c b/drivers/gpu/drm/i915/i915_gem_userptr.c index 3df77020aada..9558582c105e 100644 --- a/drivers/gpu/drm/i915/i915_gem_userptr.c +++ b/drivers/gpu/drm/i915/i915_gem_userptr.c | |||
@@ -789,8 +789,7 @@ i915_gem_userptr_ioctl(struct drm_device *dev, | |||
789 | if (offset_in_page(args->user_ptr | args->user_size)) | 789 | if (offset_in_page(args->user_ptr | args->user_size)) |
790 | return -EINVAL; | 790 | return -EINVAL; |
791 | 791 | ||
792 | if (!access_ok(args->flags & I915_USERPTR_READ_ONLY ? VERIFY_READ : VERIFY_WRITE, | 792 | if (!access_ok((char __user *)(unsigned long)args->user_ptr, args->user_size)) |
793 | (char __user *)(unsigned long)args->user_ptr, args->user_size)) | ||
794 | return -EFAULT; | 793 | return -EFAULT; |
795 | 794 | ||
796 | if (args->flags & I915_USERPTR_READ_ONLY) { | 795 | if (args->flags & I915_USERPTR_READ_ONLY) { |
diff --git a/drivers/gpu/drm/i915/i915_ioc32.c b/drivers/gpu/drm/i915/i915_ioc32.c index 0e5c580d117c..e869daf9c8a9 100644 --- a/drivers/gpu/drm/i915/i915_ioc32.c +++ b/drivers/gpu/drm/i915/i915_ioc32.c | |||
@@ -52,7 +52,7 @@ static int compat_i915_getparam(struct file *file, unsigned int cmd, | |||
52 | return -EFAULT; | 52 | return -EFAULT; |
53 | 53 | ||
54 | request = compat_alloc_user_space(sizeof(*request)); | 54 | request = compat_alloc_user_space(sizeof(*request)); |
55 | if (!access_ok(VERIFY_WRITE, request, sizeof(*request)) || | 55 | if (!access_ok(request, sizeof(*request)) || |
56 | __put_user(req32.param, &request->param) || | 56 | __put_user(req32.param, &request->param) || |
57 | __put_user((void __user *)(unsigned long)req32.value, | 57 | __put_user((void __user *)(unsigned long)req32.value, |
58 | &request->value)) | 58 | &request->value)) |
diff --git a/drivers/gpu/drm/i915/i915_perf.c b/drivers/gpu/drm/i915/i915_perf.c index 4529edfdcfc8..2b2eb57ca71f 100644 --- a/drivers/gpu/drm/i915/i915_perf.c +++ b/drivers/gpu/drm/i915/i915_perf.c | |||
@@ -3052,7 +3052,7 @@ static struct i915_oa_reg *alloc_oa_regs(struct drm_i915_private *dev_priv, | |||
3052 | if (!n_regs) | 3052 | if (!n_regs) |
3053 | return NULL; | 3053 | return NULL; |
3054 | 3054 | ||
3055 | if (!access_ok(VERIFY_READ, regs, n_regs * sizeof(u32) * 2)) | 3055 | if (!access_ok(regs, n_regs * sizeof(u32) * 2)) |
3056 | return ERR_PTR(-EFAULT); | 3056 | return ERR_PTR(-EFAULT); |
3057 | 3057 | ||
3058 | /* No is_valid function means we're not allowing any register to be programmed. */ | 3058 | /* No is_valid function means we're not allowing any register to be programmed. */ |
diff --git a/drivers/gpu/drm/i915/i915_query.c b/drivers/gpu/drm/i915/i915_query.c index 6fc4b8eeab42..fe56465cdfd6 100644 --- a/drivers/gpu/drm/i915/i915_query.c +++ b/drivers/gpu/drm/i915/i915_query.c | |||
@@ -46,7 +46,7 @@ static int query_topology_info(struct drm_i915_private *dev_priv, | |||
46 | if (topo.flags != 0) | 46 | if (topo.flags != 0) |
47 | return -EINVAL; | 47 | return -EINVAL; |
48 | 48 | ||
49 | if (!access_ok(VERIFY_WRITE, u64_to_user_ptr(query_item->data_ptr), | 49 | if (!access_ok(u64_to_user_ptr(query_item->data_ptr), |
50 | total_length)) | 50 | total_length)) |
51 | return -EFAULT; | 51 | return -EFAULT; |
52 | 52 | ||
diff --git a/drivers/gpu/drm/msm/msm_gem_submit.c b/drivers/gpu/drm/msm/msm_gem_submit.c index a28465d90529..12b983fc0b56 100644 --- a/drivers/gpu/drm/msm/msm_gem_submit.c +++ b/drivers/gpu/drm/msm/msm_gem_submit.c | |||
@@ -77,7 +77,7 @@ void msm_gem_submit_free(struct msm_gem_submit *submit) | |||
77 | static inline unsigned long __must_check | 77 | static inline unsigned long __must_check |
78 | copy_from_user_inatomic(void *to, const void __user *from, unsigned long n) | 78 | copy_from_user_inatomic(void *to, const void __user *from, unsigned long n) |
79 | { | 79 | { |
80 | if (access_ok(VERIFY_READ, from, n)) | 80 | if (access_ok(from, n)) |
81 | return __copy_from_user_inatomic(to, from, n); | 81 | return __copy_from_user_inatomic(to, from, n); |
82 | return -EFAULT; | 82 | return -EFAULT; |
83 | } | 83 | } |
diff --git a/drivers/gpu/drm/qxl/qxl_ioctl.c b/drivers/gpu/drm/qxl/qxl_ioctl.c index 6e828158bcb0..d410e2925162 100644 --- a/drivers/gpu/drm/qxl/qxl_ioctl.c +++ b/drivers/gpu/drm/qxl/qxl_ioctl.c | |||
@@ -163,8 +163,7 @@ static int qxl_process_single_command(struct qxl_device *qdev, | |||
163 | if (cmd->command_size > PAGE_SIZE - sizeof(union qxl_release_info)) | 163 | if (cmd->command_size > PAGE_SIZE - sizeof(union qxl_release_info)) |
164 | return -EINVAL; | 164 | return -EINVAL; |
165 | 165 | ||
166 | if (!access_ok(VERIFY_READ, | 166 | if (!access_ok(u64_to_user_ptr(cmd->command), |
167 | u64_to_user_ptr(cmd->command), | ||
168 | cmd->command_size)) | 167 | cmd->command_size)) |
169 | return -EFAULT; | 168 | return -EFAULT; |
170 | 169 | ||
diff --git a/drivers/infiniband/core/uverbs_main.c b/drivers/infiniband/core/uverbs_main.c index 9f9172eb1512..fb0007aa0c27 100644 --- a/drivers/infiniband/core/uverbs_main.c +++ b/drivers/infiniband/core/uverbs_main.c | |||
@@ -611,8 +611,7 @@ static ssize_t verify_hdr(struct ib_uverbs_cmd_hdr *hdr, | |||
611 | if (hdr->out_words * 8 < method_elm->resp_size) | 611 | if (hdr->out_words * 8 < method_elm->resp_size) |
612 | return -ENOSPC; | 612 | return -ENOSPC; |
613 | 613 | ||
614 | if (!access_ok(VERIFY_WRITE, | 614 | if (!access_ok(u64_to_user_ptr(ex_hdr->response), |
615 | u64_to_user_ptr(ex_hdr->response), | ||
616 | (hdr->out_words + ex_hdr->provider_out_words) * 8)) | 615 | (hdr->out_words + ex_hdr->provider_out_words) * 8)) |
617 | return -EFAULT; | 616 | return -EFAULT; |
618 | } else { | 617 | } else { |
diff --git a/drivers/infiniband/hw/hfi1/user_exp_rcv.c b/drivers/infiniband/hw/hfi1/user_exp_rcv.c index dbe7d14a5c76..0cd71ce7cc71 100644 --- a/drivers/infiniband/hw/hfi1/user_exp_rcv.c +++ b/drivers/infiniband/hw/hfi1/user_exp_rcv.c | |||
@@ -232,7 +232,7 @@ static int pin_rcv_pages(struct hfi1_filedata *fd, struct tid_user_buf *tidbuf) | |||
232 | } | 232 | } |
233 | 233 | ||
234 | /* Verify that access is OK for the user buffer */ | 234 | /* Verify that access is OK for the user buffer */ |
235 | if (!access_ok(VERIFY_WRITE, (void __user *)vaddr, | 235 | if (!access_ok((void __user *)vaddr, |
236 | npages * PAGE_SIZE)) { | 236 | npages * PAGE_SIZE)) { |
237 | dd_dev_err(dd, "Fail vaddr %p, %u pages, !access_ok\n", | 237 | dd_dev_err(dd, "Fail vaddr %p, %u pages, !access_ok\n", |
238 | (void *)vaddr, npages); | 238 | (void *)vaddr, npages); |
diff --git a/drivers/infiniband/hw/qib/qib_file_ops.c b/drivers/infiniband/hw/qib/qib_file_ops.c index 98e1ce14fa2a..78fa634de98a 100644 --- a/drivers/infiniband/hw/qib/qib_file_ops.c +++ b/drivers/infiniband/hw/qib/qib_file_ops.c | |||
@@ -343,7 +343,7 @@ static int qib_tid_update(struct qib_ctxtdata *rcd, struct file *fp, | |||
343 | 343 | ||
344 | /* virtual address of first page in transfer */ | 344 | /* virtual address of first page in transfer */ |
345 | vaddr = ti->tidvaddr; | 345 | vaddr = ti->tidvaddr; |
346 | if (!access_ok(VERIFY_WRITE, (void __user *) vaddr, | 346 | if (!access_ok((void __user *) vaddr, |
347 | cnt * PAGE_SIZE)) { | 347 | cnt * PAGE_SIZE)) { |
348 | ret = -EFAULT; | 348 | ret = -EFAULT; |
349 | goto done; | 349 | goto done; |
diff --git a/drivers/isdn/capi/kcapi.c b/drivers/isdn/capi/kcapi.c index 0ff517d3c98f..a4ceb61c5b60 100644 --- a/drivers/isdn/capi/kcapi.c +++ b/drivers/isdn/capi/kcapi.c | |||
@@ -852,7 +852,7 @@ u16 capi20_get_manufacturer(u32 contr, u8 *buf) | |||
852 | u16 ret; | 852 | u16 ret; |
853 | 853 | ||
854 | if (contr == 0) { | 854 | if (contr == 0) { |
855 | strlcpy(buf, capi_manufakturer, CAPI_MANUFACTURER_LEN); | 855 | strncpy(buf, capi_manufakturer, CAPI_MANUFACTURER_LEN); |
856 | return CAPI_NOERROR; | 856 | return CAPI_NOERROR; |
857 | } | 857 | } |
858 | 858 | ||
@@ -860,7 +860,7 @@ u16 capi20_get_manufacturer(u32 contr, u8 *buf) | |||
860 | 860 | ||
861 | ctr = get_capi_ctr_by_nr(contr); | 861 | ctr = get_capi_ctr_by_nr(contr); |
862 | if (ctr && ctr->state == CAPI_CTR_RUNNING) { | 862 | if (ctr && ctr->state == CAPI_CTR_RUNNING) { |
863 | strlcpy(buf, ctr->manu, CAPI_MANUFACTURER_LEN); | 863 | strncpy(buf, ctr->manu, CAPI_MANUFACTURER_LEN); |
864 | ret = CAPI_NOERROR; | 864 | ret = CAPI_NOERROR; |
865 | } else | 865 | } else |
866 | ret = CAPI_REGNOTINSTALLED; | 866 | ret = CAPI_REGNOTINSTALLED; |
diff --git a/drivers/isdn/hisax/hfc_pci.c b/drivers/isdn/hisax/hfc_pci.c index 5b719b561860..81dd465afcf4 100644 --- a/drivers/isdn/hisax/hfc_pci.c +++ b/drivers/isdn/hisax/hfc_pci.c | |||
@@ -1169,11 +1169,13 @@ HFCPCI_l1hw(struct PStack *st, int pr, void *arg) | |||
1169 | if (cs->debug & L1_DEB_LAPD) | 1169 | if (cs->debug & L1_DEB_LAPD) |
1170 | debugl1(cs, "-> PH_REQUEST_PULL"); | 1170 | debugl1(cs, "-> PH_REQUEST_PULL"); |
1171 | #endif | 1171 | #endif |
1172 | spin_lock_irqsave(&cs->lock, flags); | ||
1172 | if (!cs->tx_skb) { | 1173 | if (!cs->tx_skb) { |
1173 | test_and_clear_bit(FLG_L1_PULL_REQ, &st->l1.Flags); | 1174 | test_and_clear_bit(FLG_L1_PULL_REQ, &st->l1.Flags); |
1174 | st->l1.l1l2(st, PH_PULL | CONFIRM, NULL); | 1175 | st->l1.l1l2(st, PH_PULL | CONFIRM, NULL); |
1175 | } else | 1176 | } else |
1176 | test_and_set_bit(FLG_L1_PULL_REQ, &st->l1.Flags); | 1177 | test_and_set_bit(FLG_L1_PULL_REQ, &st->l1.Flags); |
1178 | spin_unlock_irqrestore(&cs->lock, flags); | ||
1177 | break; | 1179 | break; |
1178 | case (HW_RESET | REQUEST): | 1180 | case (HW_RESET | REQUEST): |
1179 | spin_lock_irqsave(&cs->lock, flags); | 1181 | spin_lock_irqsave(&cs->lock, flags); |
diff --git a/drivers/macintosh/ans-lcd.c b/drivers/macintosh/ans-lcd.c index ef0c2366cf59..400960cf04d5 100644 --- a/drivers/macintosh/ans-lcd.c +++ b/drivers/macintosh/ans-lcd.c | |||
@@ -64,7 +64,7 @@ anslcd_write( struct file * file, const char __user * buf, | |||
64 | printk(KERN_DEBUG "LCD: write\n"); | 64 | printk(KERN_DEBUG "LCD: write\n"); |
65 | #endif | 65 | #endif |
66 | 66 | ||
67 | if (!access_ok(VERIFY_READ, buf, count)) | 67 | if (!access_ok(buf, count)) |
68 | return -EFAULT; | 68 | return -EFAULT; |
69 | 69 | ||
70 | mutex_lock(&anslcd_mutex); | 70 | mutex_lock(&anslcd_mutex); |
diff --git a/drivers/macintosh/via-pmu.c b/drivers/macintosh/via-pmu.c index ac0cf37d6239..21d532a78fa4 100644 --- a/drivers/macintosh/via-pmu.c +++ b/drivers/macintosh/via-pmu.c | |||
@@ -2188,7 +2188,7 @@ pmu_read(struct file *file, char __user *buf, | |||
2188 | 2188 | ||
2189 | if (count < 1 || !pp) | 2189 | if (count < 1 || !pp) |
2190 | return -EINVAL; | 2190 | return -EINVAL; |
2191 | if (!access_ok(VERIFY_WRITE, buf, count)) | 2191 | if (!access_ok(buf, count)) |
2192 | return -EFAULT; | 2192 | return -EFAULT; |
2193 | 2193 | ||
2194 | spin_lock_irqsave(&pp->lock, flags); | 2194 | spin_lock_irqsave(&pp->lock, flags); |
diff --git a/drivers/media/pci/ivtv/ivtvfb.c b/drivers/media/pci/ivtv/ivtvfb.c index 3e02de02ffdd..8ec2525d8ef5 100644 --- a/drivers/media/pci/ivtv/ivtvfb.c +++ b/drivers/media/pci/ivtv/ivtvfb.c | |||
@@ -356,7 +356,7 @@ static int ivtvfb_prep_frame(struct ivtv *itv, int cmd, void __user *source, | |||
356 | IVTVFB_WARN("ivtvfb_prep_frame: Count not a multiple of 4 (%d)\n", count); | 356 | IVTVFB_WARN("ivtvfb_prep_frame: Count not a multiple of 4 (%d)\n", count); |
357 | 357 | ||
358 | /* Check Source */ | 358 | /* Check Source */ |
359 | if (!access_ok(VERIFY_READ, source + dest_offset, count)) { | 359 | if (!access_ok(source + dest_offset, count)) { |
360 | IVTVFB_WARN("Invalid userspace pointer %p\n", source); | 360 | IVTVFB_WARN("Invalid userspace pointer %p\n", source); |
361 | 361 | ||
362 | IVTVFB_DEBUG_WARN("access_ok() failed for offset 0x%08lx source %p count %d\n", | 362 | IVTVFB_DEBUG_WARN("access_ok() failed for offset 0x%08lx source %p count %d\n", |
diff --git a/drivers/media/v4l2-core/v4l2-compat-ioctl32.c b/drivers/media/v4l2-core/v4l2-compat-ioctl32.c index fe4577a46869..73dac1d8d4f6 100644 --- a/drivers/media/v4l2-core/v4l2-compat-ioctl32.c +++ b/drivers/media/v4l2-core/v4l2-compat-ioctl32.c | |||
@@ -158,7 +158,7 @@ static int get_v4l2_window32(struct v4l2_window __user *p64, | |||
158 | compat_caddr_t p; | 158 | compat_caddr_t p; |
159 | u32 clipcount; | 159 | u32 clipcount; |
160 | 160 | ||
161 | if (!access_ok(VERIFY_READ, p32, sizeof(*p32)) || | 161 | if (!access_ok(p32, sizeof(*p32)) || |
162 | copy_in_user(&p64->w, &p32->w, sizeof(p32->w)) || | 162 | copy_in_user(&p64->w, &p32->w, sizeof(p32->w)) || |
163 | assign_in_user(&p64->field, &p32->field) || | 163 | assign_in_user(&p64->field, &p32->field) || |
164 | assign_in_user(&p64->chromakey, &p32->chromakey) || | 164 | assign_in_user(&p64->chromakey, &p32->chromakey) || |
@@ -283,7 +283,7 @@ static int __bufsize_v4l2_format(struct v4l2_format32 __user *p32, u32 *size) | |||
283 | 283 | ||
284 | static int bufsize_v4l2_format(struct v4l2_format32 __user *p32, u32 *size) | 284 | static int bufsize_v4l2_format(struct v4l2_format32 __user *p32, u32 *size) |
285 | { | 285 | { |
286 | if (!access_ok(VERIFY_READ, p32, sizeof(*p32))) | 286 | if (!access_ok(p32, sizeof(*p32))) |
287 | return -EFAULT; | 287 | return -EFAULT; |
288 | return __bufsize_v4l2_format(p32, size); | 288 | return __bufsize_v4l2_format(p32, size); |
289 | } | 289 | } |
@@ -335,7 +335,7 @@ static int get_v4l2_format32(struct v4l2_format __user *p64, | |||
335 | struct v4l2_format32 __user *p32, | 335 | struct v4l2_format32 __user *p32, |
336 | void __user *aux_buf, u32 aux_space) | 336 | void __user *aux_buf, u32 aux_space) |
337 | { | 337 | { |
338 | if (!access_ok(VERIFY_READ, p32, sizeof(*p32))) | 338 | if (!access_ok(p32, sizeof(*p32))) |
339 | return -EFAULT; | 339 | return -EFAULT; |
340 | return __get_v4l2_format32(p64, p32, aux_buf, aux_space); | 340 | return __get_v4l2_format32(p64, p32, aux_buf, aux_space); |
341 | } | 341 | } |
@@ -343,7 +343,7 @@ static int get_v4l2_format32(struct v4l2_format __user *p64, | |||
343 | static int bufsize_v4l2_create(struct v4l2_create_buffers32 __user *p32, | 343 | static int bufsize_v4l2_create(struct v4l2_create_buffers32 __user *p32, |
344 | u32 *size) | 344 | u32 *size) |
345 | { | 345 | { |
346 | if (!access_ok(VERIFY_READ, p32, sizeof(*p32))) | 346 | if (!access_ok(p32, sizeof(*p32))) |
347 | return -EFAULT; | 347 | return -EFAULT; |
348 | return __bufsize_v4l2_format(&p32->format, size); | 348 | return __bufsize_v4l2_format(&p32->format, size); |
349 | } | 349 | } |
@@ -352,7 +352,7 @@ static int get_v4l2_create32(struct v4l2_create_buffers __user *p64, | |||
352 | struct v4l2_create_buffers32 __user *p32, | 352 | struct v4l2_create_buffers32 __user *p32, |
353 | void __user *aux_buf, u32 aux_space) | 353 | void __user *aux_buf, u32 aux_space) |
354 | { | 354 | { |
355 | if (!access_ok(VERIFY_READ, p32, sizeof(*p32)) || | 355 | if (!access_ok(p32, sizeof(*p32)) || |
356 | copy_in_user(p64, p32, | 356 | copy_in_user(p64, p32, |
357 | offsetof(struct v4l2_create_buffers32, format))) | 357 | offsetof(struct v4l2_create_buffers32, format))) |
358 | return -EFAULT; | 358 | return -EFAULT; |
@@ -404,7 +404,7 @@ static int __put_v4l2_format32(struct v4l2_format __user *p64, | |||
404 | static int put_v4l2_format32(struct v4l2_format __user *p64, | 404 | static int put_v4l2_format32(struct v4l2_format __user *p64, |
405 | struct v4l2_format32 __user *p32) | 405 | struct v4l2_format32 __user *p32) |
406 | { | 406 | { |
407 | if (!access_ok(VERIFY_WRITE, p32, sizeof(*p32))) | 407 | if (!access_ok(p32, sizeof(*p32))) |
408 | return -EFAULT; | 408 | return -EFAULT; |
409 | return __put_v4l2_format32(p64, p32); | 409 | return __put_v4l2_format32(p64, p32); |
410 | } | 410 | } |
@@ -412,7 +412,7 @@ static int put_v4l2_format32(struct v4l2_format __user *p64, | |||
412 | static int put_v4l2_create32(struct v4l2_create_buffers __user *p64, | 412 | static int put_v4l2_create32(struct v4l2_create_buffers __user *p64, |
413 | struct v4l2_create_buffers32 __user *p32) | 413 | struct v4l2_create_buffers32 __user *p32) |
414 | { | 414 | { |
415 | if (!access_ok(VERIFY_WRITE, p32, sizeof(*p32)) || | 415 | if (!access_ok(p32, sizeof(*p32)) || |
416 | copy_in_user(p32, p64, | 416 | copy_in_user(p32, p64, |
417 | offsetof(struct v4l2_create_buffers32, format)) || | 417 | offsetof(struct v4l2_create_buffers32, format)) || |
418 | assign_in_user(&p32->capabilities, &p64->capabilities) || | 418 | assign_in_user(&p32->capabilities, &p64->capabilities) || |
@@ -434,7 +434,7 @@ static int get_v4l2_standard32(struct v4l2_standard __user *p64, | |||
434 | struct v4l2_standard32 __user *p32) | 434 | struct v4l2_standard32 __user *p32) |
435 | { | 435 | { |
436 | /* other fields are not set by the user, nor used by the driver */ | 436 | /* other fields are not set by the user, nor used by the driver */ |
437 | if (!access_ok(VERIFY_READ, p32, sizeof(*p32)) || | 437 | if (!access_ok(p32, sizeof(*p32)) || |
438 | assign_in_user(&p64->index, &p32->index)) | 438 | assign_in_user(&p64->index, &p32->index)) |
439 | return -EFAULT; | 439 | return -EFAULT; |
440 | return 0; | 440 | return 0; |
@@ -443,7 +443,7 @@ static int get_v4l2_standard32(struct v4l2_standard __user *p64, | |||
443 | static int put_v4l2_standard32(struct v4l2_standard __user *p64, | 443 | static int put_v4l2_standard32(struct v4l2_standard __user *p64, |
444 | struct v4l2_standard32 __user *p32) | 444 | struct v4l2_standard32 __user *p32) |
445 | { | 445 | { |
446 | if (!access_ok(VERIFY_WRITE, p32, sizeof(*p32)) || | 446 | if (!access_ok(p32, sizeof(*p32)) || |
447 | assign_in_user(&p32->index, &p64->index) || | 447 | assign_in_user(&p32->index, &p64->index) || |
448 | assign_in_user(&p32->id, &p64->id) || | 448 | assign_in_user(&p32->id, &p64->id) || |
449 | copy_in_user(p32->name, p64->name, sizeof(p32->name)) || | 449 | copy_in_user(p32->name, p64->name, sizeof(p32->name)) || |
@@ -560,7 +560,7 @@ static int bufsize_v4l2_buffer(struct v4l2_buffer32 __user *p32, u32 *size) | |||
560 | u32 type; | 560 | u32 type; |
561 | u32 length; | 561 | u32 length; |
562 | 562 | ||
563 | if (!access_ok(VERIFY_READ, p32, sizeof(*p32)) || | 563 | if (!access_ok(p32, sizeof(*p32)) || |
564 | get_user(type, &p32->type) || | 564 | get_user(type, &p32->type) || |
565 | get_user(length, &p32->length)) | 565 | get_user(length, &p32->length)) |
566 | return -EFAULT; | 566 | return -EFAULT; |
@@ -593,7 +593,7 @@ static int get_v4l2_buffer32(struct v4l2_buffer __user *p64, | |||
593 | compat_caddr_t p; | 593 | compat_caddr_t p; |
594 | int ret; | 594 | int ret; |
595 | 595 | ||
596 | if (!access_ok(VERIFY_READ, p32, sizeof(*p32)) || | 596 | if (!access_ok(p32, sizeof(*p32)) || |
597 | assign_in_user(&p64->index, &p32->index) || | 597 | assign_in_user(&p64->index, &p32->index) || |
598 | get_user(type, &p32->type) || | 598 | get_user(type, &p32->type) || |
599 | put_user(type, &p64->type) || | 599 | put_user(type, &p64->type) || |
@@ -632,7 +632,7 @@ static int get_v4l2_buffer32(struct v4l2_buffer __user *p64, | |||
632 | return -EFAULT; | 632 | return -EFAULT; |
633 | 633 | ||
634 | uplane32 = compat_ptr(p); | 634 | uplane32 = compat_ptr(p); |
635 | if (!access_ok(VERIFY_READ, uplane32, | 635 | if (!access_ok(uplane32, |
636 | num_planes * sizeof(*uplane32))) | 636 | num_planes * sizeof(*uplane32))) |
637 | return -EFAULT; | 637 | return -EFAULT; |
638 | 638 | ||
@@ -691,7 +691,7 @@ static int put_v4l2_buffer32(struct v4l2_buffer __user *p64, | |||
691 | compat_caddr_t p; | 691 | compat_caddr_t p; |
692 | int ret; | 692 | int ret; |
693 | 693 | ||
694 | if (!access_ok(VERIFY_WRITE, p32, sizeof(*p32)) || | 694 | if (!access_ok(p32, sizeof(*p32)) || |
695 | assign_in_user(&p32->index, &p64->index) || | 695 | assign_in_user(&p32->index, &p64->index) || |
696 | get_user(type, &p64->type) || | 696 | get_user(type, &p64->type) || |
697 | put_user(type, &p32->type) || | 697 | put_user(type, &p32->type) || |
@@ -781,7 +781,7 @@ static int get_v4l2_framebuffer32(struct v4l2_framebuffer __user *p64, | |||
781 | { | 781 | { |
782 | compat_caddr_t tmp; | 782 | compat_caddr_t tmp; |
783 | 783 | ||
784 | if (!access_ok(VERIFY_READ, p32, sizeof(*p32)) || | 784 | if (!access_ok(p32, sizeof(*p32)) || |
785 | get_user(tmp, &p32->base) || | 785 | get_user(tmp, &p32->base) || |
786 | put_user_force(compat_ptr(tmp), &p64->base) || | 786 | put_user_force(compat_ptr(tmp), &p64->base) || |
787 | assign_in_user(&p64->capability, &p32->capability) || | 787 | assign_in_user(&p64->capability, &p32->capability) || |
@@ -796,7 +796,7 @@ static int put_v4l2_framebuffer32(struct v4l2_framebuffer __user *p64, | |||
796 | { | 796 | { |
797 | void *base; | 797 | void *base; |
798 | 798 | ||
799 | if (!access_ok(VERIFY_WRITE, p32, sizeof(*p32)) || | 799 | if (!access_ok(p32, sizeof(*p32)) || |
800 | get_user(base, &p64->base) || | 800 | get_user(base, &p64->base) || |
801 | put_user(ptr_to_compat((void __user *)base), &p32->base) || | 801 | put_user(ptr_to_compat((void __user *)base), &p32->base) || |
802 | assign_in_user(&p32->capability, &p64->capability) || | 802 | assign_in_user(&p32->capability, &p64->capability) || |
@@ -893,7 +893,7 @@ static int bufsize_v4l2_ext_controls(struct v4l2_ext_controls32 __user *p32, | |||
893 | { | 893 | { |
894 | u32 count; | 894 | u32 count; |
895 | 895 | ||
896 | if (!access_ok(VERIFY_READ, p32, sizeof(*p32)) || | 896 | if (!access_ok(p32, sizeof(*p32)) || |
897 | get_user(count, &p32->count)) | 897 | get_user(count, &p32->count)) |
898 | return -EFAULT; | 898 | return -EFAULT; |
899 | if (count > V4L2_CID_MAX_CTRLS) | 899 | if (count > V4L2_CID_MAX_CTRLS) |
@@ -913,7 +913,7 @@ static int get_v4l2_ext_controls32(struct file *file, | |||
913 | u32 n; | 913 | u32 n; |
914 | compat_caddr_t p; | 914 | compat_caddr_t p; |
915 | 915 | ||
916 | if (!access_ok(VERIFY_READ, p32, sizeof(*p32)) || | 916 | if (!access_ok(p32, sizeof(*p32)) || |
917 | assign_in_user(&p64->which, &p32->which) || | 917 | assign_in_user(&p64->which, &p32->which) || |
918 | get_user(count, &p32->count) || | 918 | get_user(count, &p32->count) || |
919 | put_user(count, &p64->count) || | 919 | put_user(count, &p64->count) || |
@@ -929,7 +929,7 @@ static int get_v4l2_ext_controls32(struct file *file, | |||
929 | if (get_user(p, &p32->controls)) | 929 | if (get_user(p, &p32->controls)) |
930 | return -EFAULT; | 930 | return -EFAULT; |
931 | ucontrols = compat_ptr(p); | 931 | ucontrols = compat_ptr(p); |
932 | if (!access_ok(VERIFY_READ, ucontrols, count * sizeof(*ucontrols))) | 932 | if (!access_ok(ucontrols, count * sizeof(*ucontrols))) |
933 | return -EFAULT; | 933 | return -EFAULT; |
934 | if (aux_space < count * sizeof(*kcontrols)) | 934 | if (aux_space < count * sizeof(*kcontrols)) |
935 | return -EFAULT; | 935 | return -EFAULT; |
@@ -979,7 +979,7 @@ static int put_v4l2_ext_controls32(struct file *file, | |||
979 | * with __user causes smatch warnings, so instead declare it | 979 | * with __user causes smatch warnings, so instead declare it |
980 | * without __user and cast it as a userspace pointer where needed. | 980 | * without __user and cast it as a userspace pointer where needed. |
981 | */ | 981 | */ |
982 | if (!access_ok(VERIFY_WRITE, p32, sizeof(*p32)) || | 982 | if (!access_ok(p32, sizeof(*p32)) || |
983 | assign_in_user(&p32->which, &p64->which) || | 983 | assign_in_user(&p32->which, &p64->which) || |
984 | get_user(count, &p64->count) || | 984 | get_user(count, &p64->count) || |
985 | put_user(count, &p32->count) || | 985 | put_user(count, &p32->count) || |
@@ -994,7 +994,7 @@ static int put_v4l2_ext_controls32(struct file *file, | |||
994 | if (get_user(p, &p32->controls)) | 994 | if (get_user(p, &p32->controls)) |
995 | return -EFAULT; | 995 | return -EFAULT; |
996 | ucontrols = compat_ptr(p); | 996 | ucontrols = compat_ptr(p); |
997 | if (!access_ok(VERIFY_WRITE, ucontrols, count * sizeof(*ucontrols))) | 997 | if (!access_ok(ucontrols, count * sizeof(*ucontrols))) |
998 | return -EFAULT; | 998 | return -EFAULT; |
999 | 999 | ||
1000 | for (n = 0; n < count; n++) { | 1000 | for (n = 0; n < count; n++) { |
@@ -1043,7 +1043,7 @@ struct v4l2_event32 { | |||
1043 | static int put_v4l2_event32(struct v4l2_event __user *p64, | 1043 | static int put_v4l2_event32(struct v4l2_event __user *p64, |
1044 | struct v4l2_event32 __user *p32) | 1044 | struct v4l2_event32 __user *p32) |
1045 | { | 1045 | { |
1046 | if (!access_ok(VERIFY_WRITE, p32, sizeof(*p32)) || | 1046 | if (!access_ok(p32, sizeof(*p32)) || |
1047 | assign_in_user(&p32->type, &p64->type) || | 1047 | assign_in_user(&p32->type, &p64->type) || |
1048 | copy_in_user(&p32->u, &p64->u, sizeof(p64->u)) || | 1048 | copy_in_user(&p32->u, &p64->u, sizeof(p64->u)) || |
1049 | assign_in_user(&p32->pending, &p64->pending) || | 1049 | assign_in_user(&p32->pending, &p64->pending) || |
@@ -1069,7 +1069,7 @@ static int get_v4l2_edid32(struct v4l2_edid __user *p64, | |||
1069 | { | 1069 | { |
1070 | compat_uptr_t tmp; | 1070 | compat_uptr_t tmp; |
1071 | 1071 | ||
1072 | if (!access_ok(VERIFY_READ, p32, sizeof(*p32)) || | 1072 | if (!access_ok(p32, sizeof(*p32)) || |
1073 | assign_in_user(&p64->pad, &p32->pad) || | 1073 | assign_in_user(&p64->pad, &p32->pad) || |
1074 | assign_in_user(&p64->start_block, &p32->start_block) || | 1074 | assign_in_user(&p64->start_block, &p32->start_block) || |
1075 | assign_in_user_cast(&p64->blocks, &p32->blocks) || | 1075 | assign_in_user_cast(&p64->blocks, &p32->blocks) || |
@@ -1085,7 +1085,7 @@ static int put_v4l2_edid32(struct v4l2_edid __user *p64, | |||
1085 | { | 1085 | { |
1086 | void *edid; | 1086 | void *edid; |
1087 | 1087 | ||
1088 | if (!access_ok(VERIFY_WRITE, p32, sizeof(*p32)) || | 1088 | if (!access_ok(p32, sizeof(*p32)) || |
1089 | assign_in_user(&p32->pad, &p64->pad) || | 1089 | assign_in_user(&p32->pad, &p64->pad) || |
1090 | assign_in_user(&p32->start_block, &p64->start_block) || | 1090 | assign_in_user(&p32->start_block, &p64->start_block) || |
1091 | assign_in_user(&p32->blocks, &p64->blocks) || | 1091 | assign_in_user(&p32->blocks, &p64->blocks) || |
diff --git a/drivers/misc/vmw_vmci/vmci_host.c b/drivers/misc/vmw_vmci/vmci_host.c index 5da1f3e3f997..997f92543dd4 100644 --- a/drivers/misc/vmw_vmci/vmci_host.c +++ b/drivers/misc/vmw_vmci/vmci_host.c | |||
@@ -236,7 +236,7 @@ static int vmci_host_setup_notify(struct vmci_ctx *context, | |||
236 | * about the size. | 236 | * about the size. |
237 | */ | 237 | */ |
238 | BUILD_BUG_ON(sizeof(bool) != sizeof(u8)); | 238 | BUILD_BUG_ON(sizeof(bool) != sizeof(u8)); |
239 | if (!access_ok(VERIFY_WRITE, (void __user *)uva, sizeof(u8))) | 239 | if (!access_ok((void __user *)uva, sizeof(u8))) |
240 | return VMCI_ERROR_GENERIC; | 240 | return VMCI_ERROR_GENERIC; |
241 | 241 | ||
242 | /* | 242 | /* |
diff --git a/drivers/net/dsa/bcm_sf2.c b/drivers/net/dsa/bcm_sf2.c index aa4a1f5206f1..361fbde76654 100644 --- a/drivers/net/dsa/bcm_sf2.c +++ b/drivers/net/dsa/bcm_sf2.c | |||
@@ -303,11 +303,10 @@ static int bcm_sf2_sw_mdio_write(struct mii_bus *bus, int addr, int regnum, | |||
303 | * send them to our master MDIO bus controller | 303 | * send them to our master MDIO bus controller |
304 | */ | 304 | */ |
305 | if (addr == BRCM_PSEUDO_PHY_ADDR && priv->indir_phy_mask & BIT(addr)) | 305 | if (addr == BRCM_PSEUDO_PHY_ADDR && priv->indir_phy_mask & BIT(addr)) |
306 | bcm_sf2_sw_indir_rw(priv, 0, addr, regnum, val); | 306 | return bcm_sf2_sw_indir_rw(priv, 0, addr, regnum, val); |
307 | else | 307 | else |
308 | mdiobus_write_nested(priv->master_mii_bus, addr, regnum, val); | 308 | return mdiobus_write_nested(priv->master_mii_bus, addr, |
309 | 309 | regnum, val); | |
310 | return 0; | ||
311 | } | 310 | } |
312 | 311 | ||
313 | static irqreturn_t bcm_sf2_switch_0_isr(int irq, void *dev_id) | 312 | static irqreturn_t bcm_sf2_switch_0_isr(int irq, void *dev_id) |
diff --git a/drivers/net/ethernet/atheros/atl1e/atl1e_main.c b/drivers/net/ethernet/atheros/atl1e/atl1e_main.c index 9dc6da039a6d..3164aad29bcf 100644 --- a/drivers/net/ethernet/atheros/atl1e/atl1e_main.c +++ b/drivers/net/ethernet/atheros/atl1e/atl1e_main.c | |||
@@ -473,7 +473,9 @@ static void atl1e_mdio_write(struct net_device *netdev, int phy_id, | |||
473 | { | 473 | { |
474 | struct atl1e_adapter *adapter = netdev_priv(netdev); | 474 | struct atl1e_adapter *adapter = netdev_priv(netdev); |
475 | 475 | ||
476 | atl1e_write_phy_reg(&adapter->hw, reg_num & MDIO_REG_ADDR_MASK, val); | 476 | if (atl1e_write_phy_reg(&adapter->hw, |
477 | reg_num & MDIO_REG_ADDR_MASK, val)) | ||
478 | netdev_err(netdev, "write phy register failed\n"); | ||
477 | } | 479 | } |
478 | 480 | ||
479 | static int atl1e_mii_ioctl(struct net_device *netdev, | 481 | static int atl1e_mii_ioctl(struct net_device *netdev, |
diff --git a/drivers/net/ethernet/chelsio/cxgb4/cudbg_lib.c b/drivers/net/ethernet/chelsio/cxgb4/cudbg_lib.c index 7c49681407ad..127b1f624413 100644 --- a/drivers/net/ethernet/chelsio/cxgb4/cudbg_lib.c +++ b/drivers/net/ethernet/chelsio/cxgb4/cudbg_lib.c | |||
@@ -1229,6 +1229,10 @@ int cudbg_collect_hw_sched(struct cudbg_init *pdbg_init, | |||
1229 | 1229 | ||
1230 | rc = cudbg_get_buff(pdbg_init, dbg_buff, sizeof(struct cudbg_hw_sched), | 1230 | rc = cudbg_get_buff(pdbg_init, dbg_buff, sizeof(struct cudbg_hw_sched), |
1231 | &temp_buff); | 1231 | &temp_buff); |
1232 | |||
1233 | if (rc) | ||
1234 | return rc; | ||
1235 | |||
1232 | hw_sched_buff = (struct cudbg_hw_sched *)temp_buff.data; | 1236 | hw_sched_buff = (struct cudbg_hw_sched *)temp_buff.data; |
1233 | hw_sched_buff->map = t4_read_reg(padap, TP_TX_MOD_QUEUE_REQ_MAP_A); | 1237 | hw_sched_buff->map = t4_read_reg(padap, TP_TX_MOD_QUEUE_REQ_MAP_A); |
1234 | hw_sched_buff->mode = TIMERMODE_G(t4_read_reg(padap, TP_MOD_CONFIG_A)); | 1238 | hw_sched_buff->mode = TIMERMODE_G(t4_read_reg(padap, TP_MOD_CONFIG_A)); |
diff --git a/drivers/net/ethernet/freescale/fman/fman_memac.c b/drivers/net/ethernet/freescale/fman/fman_memac.c index bc6eb30aa20f..41c6fa200e74 100644 --- a/drivers/net/ethernet/freescale/fman/fman_memac.c +++ b/drivers/net/ethernet/freescale/fman/fman_memac.c | |||
@@ -928,7 +928,7 @@ int memac_add_hash_mac_address(struct fman_mac *memac, enet_addr_t *eth_addr) | |||
928 | hash = get_mac_addr_hash_code(addr) & HASH_CTRL_ADDR_MASK; | 928 | hash = get_mac_addr_hash_code(addr) & HASH_CTRL_ADDR_MASK; |
929 | 929 | ||
930 | /* Create element to be added to the driver hash table */ | 930 | /* Create element to be added to the driver hash table */ |
931 | hash_entry = kmalloc(sizeof(*hash_entry), GFP_KERNEL); | 931 | hash_entry = kmalloc(sizeof(*hash_entry), GFP_ATOMIC); |
932 | if (!hash_entry) | 932 | if (!hash_entry) |
933 | return -ENOMEM; | 933 | return -ENOMEM; |
934 | hash_entry->addr = addr; | 934 | hash_entry->addr = addr; |
diff --git a/drivers/net/ethernet/freescale/fman/fman_tgec.c b/drivers/net/ethernet/freescale/fman/fman_tgec.c index 40705938eecc..f75b9c11b2d2 100644 --- a/drivers/net/ethernet/freescale/fman/fman_tgec.c +++ b/drivers/net/ethernet/freescale/fman/fman_tgec.c | |||
@@ -553,7 +553,7 @@ int tgec_add_hash_mac_address(struct fman_mac *tgec, enet_addr_t *eth_addr) | |||
553 | hash = (crc >> TGEC_HASH_MCAST_SHIFT) & TGEC_HASH_ADR_MSK; | 553 | hash = (crc >> TGEC_HASH_MCAST_SHIFT) & TGEC_HASH_ADR_MSK; |
554 | 554 | ||
555 | /* Create element to be added to the driver hash table */ | 555 | /* Create element to be added to the driver hash table */ |
556 | hash_entry = kmalloc(sizeof(*hash_entry), GFP_KERNEL); | 556 | hash_entry = kmalloc(sizeof(*hash_entry), GFP_ATOMIC); |
557 | if (!hash_entry) | 557 | if (!hash_entry) |
558 | return -ENOMEM; | 558 | return -ENOMEM; |
559 | hash_entry->addr = addr; | 559 | hash_entry->addr = addr; |
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c b/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c index d3b9aaf96c1c..07cd58798083 100644 --- a/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c +++ b/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c | |||
@@ -3995,17 +3995,18 @@ static int hns3_reset_notify_up_enet(struct hnae3_handle *handle) | |||
3995 | struct hns3_nic_priv *priv = netdev_priv(kinfo->netdev); | 3995 | struct hns3_nic_priv *priv = netdev_priv(kinfo->netdev); |
3996 | int ret = 0; | 3996 | int ret = 0; |
3997 | 3997 | ||
3998 | clear_bit(HNS3_NIC_STATE_RESETTING, &priv->state); | ||
3999 | |||
3998 | if (netif_running(kinfo->netdev)) { | 4000 | if (netif_running(kinfo->netdev)) { |
3999 | ret = hns3_nic_net_up(kinfo->netdev); | 4001 | ret = hns3_nic_net_open(kinfo->netdev); |
4000 | if (ret) { | 4002 | if (ret) { |
4003 | set_bit(HNS3_NIC_STATE_RESETTING, &priv->state); | ||
4001 | netdev_err(kinfo->netdev, | 4004 | netdev_err(kinfo->netdev, |
4002 | "hns net up fail, ret=%d!\n", ret); | 4005 | "hns net up fail, ret=%d!\n", ret); |
4003 | return ret; | 4006 | return ret; |
4004 | } | 4007 | } |
4005 | } | 4008 | } |
4006 | 4009 | ||
4007 | clear_bit(HNS3_NIC_STATE_RESETTING, &priv->state); | ||
4008 | |||
4009 | return ret; | 4010 | return ret; |
4010 | } | 4011 | } |
4011 | 4012 | ||
diff --git a/drivers/net/ethernet/huawei/hinic/hinic_main.c b/drivers/net/ethernet/huawei/hinic/hinic_main.c index 6d48dc62a44b..da323b9e1f62 100644 --- a/drivers/net/ethernet/huawei/hinic/hinic_main.c +++ b/drivers/net/ethernet/huawei/hinic/hinic_main.c | |||
@@ -1106,6 +1106,11 @@ static void hinic_remove(struct pci_dev *pdev) | |||
1106 | dev_info(&pdev->dev, "HiNIC driver - removed\n"); | 1106 | dev_info(&pdev->dev, "HiNIC driver - removed\n"); |
1107 | } | 1107 | } |
1108 | 1108 | ||
1109 | static void hinic_shutdown(struct pci_dev *pdev) | ||
1110 | { | ||
1111 | pci_disable_device(pdev); | ||
1112 | } | ||
1113 | |||
1109 | static const struct pci_device_id hinic_pci_table[] = { | 1114 | static const struct pci_device_id hinic_pci_table[] = { |
1110 | { PCI_VDEVICE(HUAWEI, HINIC_DEV_ID_QUAD_PORT_25GE), 0}, | 1115 | { PCI_VDEVICE(HUAWEI, HINIC_DEV_ID_QUAD_PORT_25GE), 0}, |
1111 | { PCI_VDEVICE(HUAWEI, HINIC_DEV_ID_DUAL_PORT_25GE), 0}, | 1116 | { PCI_VDEVICE(HUAWEI, HINIC_DEV_ID_DUAL_PORT_25GE), 0}, |
@@ -1119,6 +1124,7 @@ static struct pci_driver hinic_driver = { | |||
1119 | .id_table = hinic_pci_table, | 1124 | .id_table = hinic_pci_table, |
1120 | .probe = hinic_probe, | 1125 | .probe = hinic_probe, |
1121 | .remove = hinic_remove, | 1126 | .remove = hinic_remove, |
1127 | .shutdown = hinic_shutdown, | ||
1122 | }; | 1128 | }; |
1123 | 1129 | ||
1124 | module_pci_driver(hinic_driver); | 1130 | module_pci_driver(hinic_driver); |
diff --git a/drivers/net/ethernet/ibm/ibmveth.c b/drivers/net/ethernet/ibm/ibmveth.c index a4681780a55d..098d8764c0ea 100644 --- a/drivers/net/ethernet/ibm/ibmveth.c +++ b/drivers/net/ethernet/ibm/ibmveth.c | |||
@@ -1171,11 +1171,15 @@ out: | |||
1171 | 1171 | ||
1172 | map_failed_frags: | 1172 | map_failed_frags: |
1173 | last = i+1; | 1173 | last = i+1; |
1174 | for (i = 0; i < last; i++) | 1174 | for (i = 1; i < last; i++) |
1175 | dma_unmap_page(&adapter->vdev->dev, descs[i].fields.address, | 1175 | dma_unmap_page(&adapter->vdev->dev, descs[i].fields.address, |
1176 | descs[i].fields.flags_len & IBMVETH_BUF_LEN_MASK, | 1176 | descs[i].fields.flags_len & IBMVETH_BUF_LEN_MASK, |
1177 | DMA_TO_DEVICE); | 1177 | DMA_TO_DEVICE); |
1178 | 1178 | ||
1179 | dma_unmap_single(&adapter->vdev->dev, | ||
1180 | descs[0].fields.address, | ||
1181 | descs[0].fields.flags_len & IBMVETH_BUF_LEN_MASK, | ||
1182 | DMA_TO_DEVICE); | ||
1179 | map_failed: | 1183 | map_failed: |
1180 | if (!firmware_has_feature(FW_FEATURE_CMO)) | 1184 | if (!firmware_has_feature(FW_FEATURE_CMO)) |
1181 | netdev_err(netdev, "tx: unable to map xmit buffer\n"); | 1185 | netdev_err(netdev, "tx: unable to map xmit buffer\n"); |
diff --git a/drivers/net/ethernet/marvell/mvpp2/mvpp2_main.c b/drivers/net/ethernet/marvell/mvpp2/mvpp2_main.c index 6a059d6ee03f..e0875476a780 100644 --- a/drivers/net/ethernet/marvell/mvpp2/mvpp2_main.c +++ b/drivers/net/ethernet/marvell/mvpp2/mvpp2_main.c | |||
@@ -5240,6 +5240,8 @@ static int mvpp2_probe(struct platform_device *pdev) | |||
5240 | if (has_acpi_companion(&pdev->dev)) { | 5240 | if (has_acpi_companion(&pdev->dev)) { |
5241 | acpi_id = acpi_match_device(pdev->dev.driver->acpi_match_table, | 5241 | acpi_id = acpi_match_device(pdev->dev.driver->acpi_match_table, |
5242 | &pdev->dev); | 5242 | &pdev->dev); |
5243 | if (!acpi_id) | ||
5244 | return -EINVAL; | ||
5243 | priv->hw_version = (unsigned long)acpi_id->driver_data; | 5245 | priv->hw_version = (unsigned long)acpi_id->driver_data; |
5244 | } else { | 5246 | } else { |
5245 | priv->hw_version = | 5247 | priv->hw_version = |
diff --git a/drivers/net/ethernet/realtek/r8169.c b/drivers/net/ethernet/realtek/r8169.c index 99bc3de906e2..298930d39b79 100644 --- a/drivers/net/ethernet/realtek/r8169.c +++ b/drivers/net/ethernet/realtek/r8169.c | |||
@@ -1477,6 +1477,8 @@ static void __rtl8169_set_wol(struct rtl8169_private *tp, u32 wolopts) | |||
1477 | } | 1477 | } |
1478 | 1478 | ||
1479 | RTL_W8(tp, Cfg9346, Cfg9346_Lock); | 1479 | RTL_W8(tp, Cfg9346, Cfg9346_Lock); |
1480 | |||
1481 | device_set_wakeup_enable(tp_to_dev(tp), wolopts); | ||
1480 | } | 1482 | } |
1481 | 1483 | ||
1482 | static int rtl8169_set_wol(struct net_device *dev, struct ethtool_wolinfo *wol) | 1484 | static int rtl8169_set_wol(struct net_device *dev, struct ethtool_wolinfo *wol) |
@@ -1498,8 +1500,6 @@ static int rtl8169_set_wol(struct net_device *dev, struct ethtool_wolinfo *wol) | |||
1498 | 1500 | ||
1499 | rtl_unlock_work(tp); | 1501 | rtl_unlock_work(tp); |
1500 | 1502 | ||
1501 | device_set_wakeup_enable(d, tp->saved_wolopts); | ||
1502 | |||
1503 | pm_runtime_put_noidle(d); | 1503 | pm_runtime_put_noidle(d); |
1504 | 1504 | ||
1505 | return 0; | 1505 | return 0; |
diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac-sunxi.c b/drivers/net/ethernet/stmicro/stmmac/dwmac-sunxi.c index d07520fb969e..62ccbd47c1db 100644 --- a/drivers/net/ethernet/stmicro/stmmac/dwmac-sunxi.c +++ b/drivers/net/ethernet/stmicro/stmmac/dwmac-sunxi.c | |||
@@ -59,7 +59,9 @@ static int sun7i_gmac_init(struct platform_device *pdev, void *priv) | |||
59 | gmac->clk_enabled = 1; | 59 | gmac->clk_enabled = 1; |
60 | } else { | 60 | } else { |
61 | clk_set_rate(gmac->tx_clk, SUN7I_GMAC_MII_RATE); | 61 | clk_set_rate(gmac->tx_clk, SUN7I_GMAC_MII_RATE); |
62 | clk_prepare(gmac->tx_clk); | 62 | ret = clk_prepare(gmac->tx_clk); |
63 | if (ret) | ||
64 | return ret; | ||
63 | } | 65 | } |
64 | 66 | ||
65 | return 0; | 67 | return 0; |
diff --git a/drivers/net/ethernet/sun/niu.c b/drivers/net/ethernet/sun/niu.c index 9319d84bf49f..d84501441edd 100644 --- a/drivers/net/ethernet/sun/niu.c +++ b/drivers/net/ethernet/sun/niu.c | |||
@@ -8100,6 +8100,8 @@ static int niu_pci_vpd_scan_props(struct niu *np, u32 start, u32 end) | |||
8100 | start += 3; | 8100 | start += 3; |
8101 | 8101 | ||
8102 | prop_len = niu_pci_eeprom_read(np, start + 4); | 8102 | prop_len = niu_pci_eeprom_read(np, start + 4); |
8103 | if (prop_len < 0) | ||
8104 | return prop_len; | ||
8103 | err = niu_pci_vpd_get_propname(np, start + 5, namebuf, 64); | 8105 | err = niu_pci_vpd_get_propname(np, start + 5, namebuf, 64); |
8104 | if (err < 0) | 8106 | if (err < 0) |
8105 | return err; | 8107 | return err; |
@@ -8144,8 +8146,12 @@ static int niu_pci_vpd_scan_props(struct niu *np, u32 start, u32 end) | |||
8144 | netif_printk(np, probe, KERN_DEBUG, np->dev, | 8146 | netif_printk(np, probe, KERN_DEBUG, np->dev, |
8145 | "VPD_SCAN: Reading in property [%s] len[%d]\n", | 8147 | "VPD_SCAN: Reading in property [%s] len[%d]\n", |
8146 | namebuf, prop_len); | 8148 | namebuf, prop_len); |
8147 | for (i = 0; i < prop_len; i++) | 8149 | for (i = 0; i < prop_len; i++) { |
8148 | *prop_buf++ = niu_pci_eeprom_read(np, off + i); | 8150 | err = niu_pci_eeprom_read(np, off + i); |
8151 | if (err >= 0) | ||
8152 | *prop_buf = err; | ||
8153 | ++prop_buf; | ||
8154 | } | ||
8149 | } | 8155 | } |
8150 | 8156 | ||
8151 | start += len; | 8157 | start += len; |
diff --git a/drivers/net/ethernet/ti/cpts.c b/drivers/net/ethernet/ti/cpts.c index 054f78295d1d..2a9ba4acd7fa 100644 --- a/drivers/net/ethernet/ti/cpts.c +++ b/drivers/net/ethernet/ti/cpts.c | |||
@@ -590,7 +590,9 @@ struct cpts *cpts_create(struct device *dev, void __iomem *regs, | |||
590 | return ERR_CAST(cpts->refclk); | 590 | return ERR_CAST(cpts->refclk); |
591 | } | 591 | } |
592 | 592 | ||
593 | clk_prepare(cpts->refclk); | 593 | ret = clk_prepare(cpts->refclk); |
594 | if (ret) | ||
595 | return ERR_PTR(ret); | ||
594 | 596 | ||
595 | cpts->cc.read = cpts_systim_read; | 597 | cpts->cc.read = cpts_systim_read; |
596 | cpts->cc.mask = CLOCKSOURCE_MASK(32); | 598 | cpts->cc.mask = CLOCKSOURCE_MASK(32); |
diff --git a/drivers/net/hamradio/6pack.c b/drivers/net/hamradio/6pack.c index 28c749980359..a19868cba48c 100644 --- a/drivers/net/hamradio/6pack.c +++ b/drivers/net/hamradio/6pack.c | |||
@@ -523,10 +523,7 @@ static void resync_tnc(struct timer_list *t) | |||
523 | 523 | ||
524 | 524 | ||
525 | /* Start resync timer again -- the TNC might be still absent */ | 525 | /* Start resync timer again -- the TNC might be still absent */ |
526 | 526 | mod_timer(&sp->resync_t, jiffies + SIXP_RESYNC_TIMEOUT); | |
527 | del_timer(&sp->resync_t); | ||
528 | sp->resync_t.expires = jiffies + SIXP_RESYNC_TIMEOUT; | ||
529 | add_timer(&sp->resync_t); | ||
530 | } | 527 | } |
531 | 528 | ||
532 | static inline int tnc_init(struct sixpack *sp) | 529 | static inline int tnc_init(struct sixpack *sp) |
@@ -537,9 +534,7 @@ static inline int tnc_init(struct sixpack *sp) | |||
537 | 534 | ||
538 | sp->tty->ops->write(sp->tty, &inbyte, 1); | 535 | sp->tty->ops->write(sp->tty, &inbyte, 1); |
539 | 536 | ||
540 | del_timer(&sp->resync_t); | 537 | mod_timer(&sp->resync_t, jiffies + SIXP_RESYNC_TIMEOUT); |
541 | sp->resync_t.expires = jiffies + SIXP_RESYNC_TIMEOUT; | ||
542 | add_timer(&sp->resync_t); | ||
543 | 538 | ||
544 | return 0; | 539 | return 0; |
545 | } | 540 | } |
@@ -897,11 +892,8 @@ static void decode_prio_command(struct sixpack *sp, unsigned char cmd) | |||
897 | /* if the state byte has been received, the TNC is present, | 892 | /* if the state byte has been received, the TNC is present, |
898 | so the resync timer can be reset. */ | 893 | so the resync timer can be reset. */ |
899 | 894 | ||
900 | if (sp->tnc_state == TNC_IN_SYNC) { | 895 | if (sp->tnc_state == TNC_IN_SYNC) |
901 | del_timer(&sp->resync_t); | 896 | mod_timer(&sp->resync_t, jiffies + SIXP_INIT_RESYNC_TIMEOUT); |
902 | sp->resync_t.expires = jiffies + SIXP_INIT_RESYNC_TIMEOUT; | ||
903 | add_timer(&sp->resync_t); | ||
904 | } | ||
905 | 897 | ||
906 | sp->status1 = cmd & SIXP_PRIO_DATA_MASK; | 898 | sp->status1 = cmd & SIXP_PRIO_DATA_MASK; |
907 | } | 899 | } |
diff --git a/drivers/net/tap.c b/drivers/net/tap.c index 443b2694130c..c0b52e48f0e6 100644 --- a/drivers/net/tap.c +++ b/drivers/net/tap.c | |||
@@ -1177,8 +1177,6 @@ static int tap_get_user_xdp(struct tap_queue *q, struct xdp_buff *xdp) | |||
1177 | goto err_kfree; | 1177 | goto err_kfree; |
1178 | } | 1178 | } |
1179 | 1179 | ||
1180 | skb_probe_transport_header(skb, ETH_HLEN); | ||
1181 | |||
1182 | /* Move network header to the right position for VLAN tagged packets */ | 1180 | /* Move network header to the right position for VLAN tagged packets */ |
1183 | if ((skb->protocol == htons(ETH_P_8021Q) || | 1181 | if ((skb->protocol == htons(ETH_P_8021Q) || |
1184 | skb->protocol == htons(ETH_P_8021AD)) && | 1182 | skb->protocol == htons(ETH_P_8021AD)) && |
@@ -1189,6 +1187,7 @@ static int tap_get_user_xdp(struct tap_queue *q, struct xdp_buff *xdp) | |||
1189 | tap = rcu_dereference(q->tap); | 1187 | tap = rcu_dereference(q->tap); |
1190 | if (tap) { | 1188 | if (tap) { |
1191 | skb->dev = tap->dev; | 1189 | skb->dev = tap->dev; |
1190 | skb_probe_transport_header(skb, ETH_HLEN); | ||
1192 | dev_queue_xmit(skb); | 1191 | dev_queue_xmit(skb); |
1193 | } else { | 1192 | } else { |
1194 | kfree_skb(skb); | 1193 | kfree_skb(skb); |
diff --git a/drivers/net/wan/fsl_ucc_hdlc.c b/drivers/net/wan/fsl_ucc_hdlc.c index 7a42336c8af8..839fa7715709 100644 --- a/drivers/net/wan/fsl_ucc_hdlc.c +++ b/drivers/net/wan/fsl_ucc_hdlc.c | |||
@@ -1180,7 +1180,6 @@ static int ucc_hdlc_probe(struct platform_device *pdev) | |||
1180 | if (register_hdlc_device(dev)) { | 1180 | if (register_hdlc_device(dev)) { |
1181 | ret = -ENOBUFS; | 1181 | ret = -ENOBUFS; |
1182 | pr_err("ucc_hdlc: unable to register hdlc device\n"); | 1182 | pr_err("ucc_hdlc: unable to register hdlc device\n"); |
1183 | free_netdev(dev); | ||
1184 | goto free_dev; | 1183 | goto free_dev; |
1185 | } | 1184 | } |
1186 | 1185 | ||
diff --git a/drivers/net/wan/x25_asy.c b/drivers/net/wan/x25_asy.c index 1098263ab862..46c3d983b7b7 100644 --- a/drivers/net/wan/x25_asy.c +++ b/drivers/net/wan/x25_asy.c | |||
@@ -485,8 +485,10 @@ static int x25_asy_open(struct net_device *dev) | |||
485 | 485 | ||
486 | /* Cleanup */ | 486 | /* Cleanup */ |
487 | kfree(sl->xbuff); | 487 | kfree(sl->xbuff); |
488 | sl->xbuff = NULL; | ||
488 | noxbuff: | 489 | noxbuff: |
489 | kfree(sl->rbuff); | 490 | kfree(sl->rbuff); |
491 | sl->rbuff = NULL; | ||
490 | norbuff: | 492 | norbuff: |
491 | return -ENOMEM; | 493 | return -ENOMEM; |
492 | } | 494 | } |
diff --git a/drivers/pci/proc.c b/drivers/pci/proc.c index 7ac035af39f0..6fa1627ce08d 100644 --- a/drivers/pci/proc.c +++ b/drivers/pci/proc.c | |||
@@ -52,7 +52,7 @@ static ssize_t proc_bus_pci_read(struct file *file, char __user *buf, | |||
52 | nbytes = size - pos; | 52 | nbytes = size - pos; |
53 | cnt = nbytes; | 53 | cnt = nbytes; |
54 | 54 | ||
55 | if (!access_ok(VERIFY_WRITE, buf, cnt)) | 55 | if (!access_ok(buf, cnt)) |
56 | return -EINVAL; | 56 | return -EINVAL; |
57 | 57 | ||
58 | pci_config_pm_runtime_get(dev); | 58 | pci_config_pm_runtime_get(dev); |
@@ -125,7 +125,7 @@ static ssize_t proc_bus_pci_write(struct file *file, const char __user *buf, | |||
125 | nbytes = size - pos; | 125 | nbytes = size - pos; |
126 | cnt = nbytes; | 126 | cnt = nbytes; |
127 | 127 | ||
128 | if (!access_ok(VERIFY_READ, buf, cnt)) | 128 | if (!access_ok(buf, cnt)) |
129 | return -EINVAL; | 129 | return -EINVAL; |
130 | 130 | ||
131 | pci_config_pm_runtime_get(dev); | 131 | pci_config_pm_runtime_get(dev); |
diff --git a/drivers/platform/goldfish/goldfish_pipe.c b/drivers/platform/goldfish/goldfish_pipe.c index 7c639006252e..321bc673c417 100644 --- a/drivers/platform/goldfish/goldfish_pipe.c +++ b/drivers/platform/goldfish/goldfish_pipe.c | |||
@@ -416,8 +416,7 @@ static ssize_t goldfish_pipe_read_write(struct file *filp, | |||
416 | if (unlikely(bufflen == 0)) | 416 | if (unlikely(bufflen == 0)) |
417 | return 0; | 417 | return 0; |
418 | /* Check the buffer range for access */ | 418 | /* Check the buffer range for access */ |
419 | if (unlikely(!access_ok(is_write ? VERIFY_WRITE : VERIFY_READ, | 419 | if (unlikely(!access_ok(buffer, bufflen))) |
420 | buffer, bufflen))) | ||
421 | return -EFAULT; | 420 | return -EFAULT; |
422 | 421 | ||
423 | address = (unsigned long)buffer; | 422 | address = (unsigned long)buffer; |
diff --git a/drivers/pnp/isapnp/proc.c b/drivers/pnp/isapnp/proc.c index 262285e48a09..051613140812 100644 --- a/drivers/pnp/isapnp/proc.c +++ b/drivers/pnp/isapnp/proc.c | |||
@@ -47,7 +47,7 @@ static ssize_t isapnp_proc_bus_read(struct file *file, char __user * buf, | |||
47 | nbytes = size - pos; | 47 | nbytes = size - pos; |
48 | cnt = nbytes; | 48 | cnt = nbytes; |
49 | 49 | ||
50 | if (!access_ok(VERIFY_WRITE, buf, cnt)) | 50 | if (!access_ok(buf, cnt)) |
51 | return -EINVAL; | 51 | return -EINVAL; |
52 | 52 | ||
53 | isapnp_cfg_begin(dev->card->number, dev->number); | 53 | isapnp_cfg_begin(dev->card->number, dev->number); |
diff --git a/drivers/scsi/pmcraid.c b/drivers/scsi/pmcraid.c index 7c4673308f5b..e338d7a4f571 100644 --- a/drivers/scsi/pmcraid.c +++ b/drivers/scsi/pmcraid.c | |||
@@ -3600,7 +3600,7 @@ static long pmcraid_ioctl_passthrough( | |||
3600 | u32 ioasc; | 3600 | u32 ioasc; |
3601 | int request_size; | 3601 | int request_size; |
3602 | int buffer_size; | 3602 | int buffer_size; |
3603 | u8 access, direction; | 3603 | u8 direction; |
3604 | int rc = 0; | 3604 | int rc = 0; |
3605 | 3605 | ||
3606 | /* If IOA reset is in progress, wait 10 secs for reset to complete */ | 3606 | /* If IOA reset is in progress, wait 10 secs for reset to complete */ |
@@ -3649,10 +3649,8 @@ static long pmcraid_ioctl_passthrough( | |||
3649 | request_size = le32_to_cpu(buffer->ioarcb.data_transfer_length); | 3649 | request_size = le32_to_cpu(buffer->ioarcb.data_transfer_length); |
3650 | 3650 | ||
3651 | if (buffer->ioarcb.request_flags0 & TRANSFER_DIR_WRITE) { | 3651 | if (buffer->ioarcb.request_flags0 & TRANSFER_DIR_WRITE) { |
3652 | access = VERIFY_READ; | ||
3653 | direction = DMA_TO_DEVICE; | 3652 | direction = DMA_TO_DEVICE; |
3654 | } else { | 3653 | } else { |
3655 | access = VERIFY_WRITE; | ||
3656 | direction = DMA_FROM_DEVICE; | 3654 | direction = DMA_FROM_DEVICE; |
3657 | } | 3655 | } |
3658 | 3656 | ||
diff --git a/drivers/scsi/scsi_ioctl.c b/drivers/scsi/scsi_ioctl.c index cc30fccc1a2e..840d96fe81bc 100644 --- a/drivers/scsi/scsi_ioctl.c +++ b/drivers/scsi/scsi_ioctl.c | |||
@@ -221,7 +221,7 @@ int scsi_ioctl(struct scsi_device *sdev, int cmd, void __user *arg) | |||
221 | 221 | ||
222 | switch (cmd) { | 222 | switch (cmd) { |
223 | case SCSI_IOCTL_GET_IDLUN: | 223 | case SCSI_IOCTL_GET_IDLUN: |
224 | if (!access_ok(VERIFY_WRITE, arg, sizeof(struct scsi_idlun))) | 224 | if (!access_ok(arg, sizeof(struct scsi_idlun))) |
225 | return -EFAULT; | 225 | return -EFAULT; |
226 | 226 | ||
227 | __put_user((sdev->id & 0xff) | 227 | __put_user((sdev->id & 0xff) |
diff --git a/drivers/scsi/sg.c b/drivers/scsi/sg.c index 4e27460ec926..d3f15319b9b3 100644 --- a/drivers/scsi/sg.c +++ b/drivers/scsi/sg.c | |||
@@ -434,7 +434,7 @@ sg_read(struct file *filp, char __user *buf, size_t count, loff_t * ppos) | |||
434 | SCSI_LOG_TIMEOUT(3, sg_printk(KERN_INFO, sdp, | 434 | SCSI_LOG_TIMEOUT(3, sg_printk(KERN_INFO, sdp, |
435 | "sg_read: count=%d\n", (int) count)); | 435 | "sg_read: count=%d\n", (int) count)); |
436 | 436 | ||
437 | if (!access_ok(VERIFY_WRITE, buf, count)) | 437 | if (!access_ok(buf, count)) |
438 | return -EFAULT; | 438 | return -EFAULT; |
439 | if (sfp->force_packid && (count >= SZ_SG_HEADER)) { | 439 | if (sfp->force_packid && (count >= SZ_SG_HEADER)) { |
440 | old_hdr = kmalloc(SZ_SG_HEADER, GFP_KERNEL); | 440 | old_hdr = kmalloc(SZ_SG_HEADER, GFP_KERNEL); |
@@ -632,7 +632,7 @@ sg_write(struct file *filp, const char __user *buf, size_t count, loff_t * ppos) | |||
632 | scsi_block_when_processing_errors(sdp->device))) | 632 | scsi_block_when_processing_errors(sdp->device))) |
633 | return -ENXIO; | 633 | return -ENXIO; |
634 | 634 | ||
635 | if (!access_ok(VERIFY_READ, buf, count)) | 635 | if (!access_ok(buf, count)) |
636 | return -EFAULT; /* protects following copy_from_user()s + get_user()s */ | 636 | return -EFAULT; /* protects following copy_from_user()s + get_user()s */ |
637 | if (count < SZ_SG_HEADER) | 637 | if (count < SZ_SG_HEADER) |
638 | return -EIO; | 638 | return -EIO; |
@@ -729,7 +729,7 @@ sg_new_write(Sg_fd *sfp, struct file *file, const char __user *buf, | |||
729 | 729 | ||
730 | if (count < SZ_SG_IO_HDR) | 730 | if (count < SZ_SG_IO_HDR) |
731 | return -EINVAL; | 731 | return -EINVAL; |
732 | if (!access_ok(VERIFY_READ, buf, count)) | 732 | if (!access_ok(buf, count)) |
733 | return -EFAULT; /* protects following copy_from_user()s + get_user()s */ | 733 | return -EFAULT; /* protects following copy_from_user()s + get_user()s */ |
734 | 734 | ||
735 | sfp->cmd_q = 1; /* when sg_io_hdr seen, set command queuing on */ | 735 | sfp->cmd_q = 1; /* when sg_io_hdr seen, set command queuing on */ |
@@ -768,7 +768,7 @@ sg_new_write(Sg_fd *sfp, struct file *file, const char __user *buf, | |||
768 | sg_remove_request(sfp, srp); | 768 | sg_remove_request(sfp, srp); |
769 | return -EMSGSIZE; | 769 | return -EMSGSIZE; |
770 | } | 770 | } |
771 | if (!access_ok(VERIFY_READ, hp->cmdp, hp->cmd_len)) { | 771 | if (!access_ok(hp->cmdp, hp->cmd_len)) { |
772 | sg_remove_request(sfp, srp); | 772 | sg_remove_request(sfp, srp); |
773 | return -EFAULT; /* protects following copy_from_user()s + get_user()s */ | 773 | return -EFAULT; /* protects following copy_from_user()s + get_user()s */ |
774 | } | 774 | } |
@@ -922,7 +922,7 @@ sg_ioctl(struct file *filp, unsigned int cmd_in, unsigned long arg) | |||
922 | return -ENODEV; | 922 | return -ENODEV; |
923 | if (!scsi_block_when_processing_errors(sdp->device)) | 923 | if (!scsi_block_when_processing_errors(sdp->device)) |
924 | return -ENXIO; | 924 | return -ENXIO; |
925 | if (!access_ok(VERIFY_WRITE, p, SZ_SG_IO_HDR)) | 925 | if (!access_ok(p, SZ_SG_IO_HDR)) |
926 | return -EFAULT; | 926 | return -EFAULT; |
927 | result = sg_new_write(sfp, filp, p, SZ_SG_IO_HDR, | 927 | result = sg_new_write(sfp, filp, p, SZ_SG_IO_HDR, |
928 | 1, read_only, 1, &srp); | 928 | 1, read_only, 1, &srp); |
@@ -968,7 +968,7 @@ sg_ioctl(struct file *filp, unsigned int cmd_in, unsigned long arg) | |||
968 | case SG_GET_LOW_DMA: | 968 | case SG_GET_LOW_DMA: |
969 | return put_user((int) sdp->device->host->unchecked_isa_dma, ip); | 969 | return put_user((int) sdp->device->host->unchecked_isa_dma, ip); |
970 | case SG_GET_SCSI_ID: | 970 | case SG_GET_SCSI_ID: |
971 | if (!access_ok(VERIFY_WRITE, p, sizeof (sg_scsi_id_t))) | 971 | if (!access_ok(p, sizeof (sg_scsi_id_t))) |
972 | return -EFAULT; | 972 | return -EFAULT; |
973 | else { | 973 | else { |
974 | sg_scsi_id_t __user *sg_idp = p; | 974 | sg_scsi_id_t __user *sg_idp = p; |
@@ -997,7 +997,7 @@ sg_ioctl(struct file *filp, unsigned int cmd_in, unsigned long arg) | |||
997 | sfp->force_packid = val ? 1 : 0; | 997 | sfp->force_packid = val ? 1 : 0; |
998 | return 0; | 998 | return 0; |
999 | case SG_GET_PACK_ID: | 999 | case SG_GET_PACK_ID: |
1000 | if (!access_ok(VERIFY_WRITE, ip, sizeof (int))) | 1000 | if (!access_ok(ip, sizeof (int))) |
1001 | return -EFAULT; | 1001 | return -EFAULT; |
1002 | read_lock_irqsave(&sfp->rq_list_lock, iflags); | 1002 | read_lock_irqsave(&sfp->rq_list_lock, iflags); |
1003 | list_for_each_entry(srp, &sfp->rq_list, entry) { | 1003 | list_for_each_entry(srp, &sfp->rq_list, entry) { |
@@ -1078,7 +1078,7 @@ sg_ioctl(struct file *filp, unsigned int cmd_in, unsigned long arg) | |||
1078 | val = (sdp->device ? 1 : 0); | 1078 | val = (sdp->device ? 1 : 0); |
1079 | return put_user(val, ip); | 1079 | return put_user(val, ip); |
1080 | case SG_GET_REQUEST_TABLE: | 1080 | case SG_GET_REQUEST_TABLE: |
1081 | if (!access_ok(VERIFY_WRITE, p, SZ_SG_REQ_INFO * SG_MAX_QUEUE)) | 1081 | if (!access_ok(p, SZ_SG_REQ_INFO * SG_MAX_QUEUE)) |
1082 | return -EFAULT; | 1082 | return -EFAULT; |
1083 | else { | 1083 | else { |
1084 | sg_req_info_t *rinfo; | 1084 | sg_req_info_t *rinfo; |
diff --git a/drivers/staging/comedi/comedi_compat32.c b/drivers/staging/comedi/comedi_compat32.c index fa9d239474ee..36a3564ba1fb 100644 --- a/drivers/staging/comedi/comedi_compat32.c +++ b/drivers/staging/comedi/comedi_compat32.c | |||
@@ -102,8 +102,8 @@ static int compat_chaninfo(struct file *file, unsigned long arg) | |||
102 | chaninfo = compat_alloc_user_space(sizeof(*chaninfo)); | 102 | chaninfo = compat_alloc_user_space(sizeof(*chaninfo)); |
103 | 103 | ||
104 | /* Copy chaninfo structure. Ignore unused members. */ | 104 | /* Copy chaninfo structure. Ignore unused members. */ |
105 | if (!access_ok(VERIFY_READ, chaninfo32, sizeof(*chaninfo32)) || | 105 | if (!access_ok(chaninfo32, sizeof(*chaninfo32)) || |
106 | !access_ok(VERIFY_WRITE, chaninfo, sizeof(*chaninfo))) | 106 | !access_ok(chaninfo, sizeof(*chaninfo))) |
107 | return -EFAULT; | 107 | return -EFAULT; |
108 | 108 | ||
109 | err = 0; | 109 | err = 0; |
@@ -136,8 +136,8 @@ static int compat_rangeinfo(struct file *file, unsigned long arg) | |||
136 | rangeinfo = compat_alloc_user_space(sizeof(*rangeinfo)); | 136 | rangeinfo = compat_alloc_user_space(sizeof(*rangeinfo)); |
137 | 137 | ||
138 | /* Copy rangeinfo structure. */ | 138 | /* Copy rangeinfo structure. */ |
139 | if (!access_ok(VERIFY_READ, rangeinfo32, sizeof(*rangeinfo32)) || | 139 | if (!access_ok(rangeinfo32, sizeof(*rangeinfo32)) || |
140 | !access_ok(VERIFY_WRITE, rangeinfo, sizeof(*rangeinfo))) | 140 | !access_ok(rangeinfo, sizeof(*rangeinfo))) |
141 | return -EFAULT; | 141 | return -EFAULT; |
142 | 142 | ||
143 | err = 0; | 143 | err = 0; |
@@ -163,8 +163,8 @@ static int get_compat_cmd(struct comedi_cmd __user *cmd, | |||
163 | } temp; | 163 | } temp; |
164 | 164 | ||
165 | /* Copy cmd structure. */ | 165 | /* Copy cmd structure. */ |
166 | if (!access_ok(VERIFY_READ, cmd32, sizeof(*cmd32)) || | 166 | if (!access_ok(cmd32, sizeof(*cmd32)) || |
167 | !access_ok(VERIFY_WRITE, cmd, sizeof(*cmd))) | 167 | !access_ok(cmd, sizeof(*cmd))) |
168 | return -EFAULT; | 168 | return -EFAULT; |
169 | 169 | ||
170 | err = 0; | 170 | err = 0; |
@@ -217,8 +217,8 @@ static int put_compat_cmd(struct comedi32_cmd_struct __user *cmd32, | |||
217 | * Assume the pointer values are already valid. | 217 | * Assume the pointer values are already valid. |
218 | * (Could use ptr_to_compat() to set them.) | 218 | * (Could use ptr_to_compat() to set them.) |
219 | */ | 219 | */ |
220 | if (!access_ok(VERIFY_READ, cmd, sizeof(*cmd)) || | 220 | if (!access_ok(cmd, sizeof(*cmd)) || |
221 | !access_ok(VERIFY_WRITE, cmd32, sizeof(*cmd32))) | 221 | !access_ok(cmd32, sizeof(*cmd32))) |
222 | return -EFAULT; | 222 | return -EFAULT; |
223 | 223 | ||
224 | err = 0; | 224 | err = 0; |
@@ -317,8 +317,8 @@ static int get_compat_insn(struct comedi_insn __user *insn, | |||
317 | 317 | ||
318 | /* Copy insn structure. Ignore the unused members. */ | 318 | /* Copy insn structure. Ignore the unused members. */ |
319 | err = 0; | 319 | err = 0; |
320 | if (!access_ok(VERIFY_READ, insn32, sizeof(*insn32)) || | 320 | if (!access_ok(insn32, sizeof(*insn32)) || |
321 | !access_ok(VERIFY_WRITE, insn, sizeof(*insn))) | 321 | !access_ok(insn, sizeof(*insn))) |
322 | return -EFAULT; | 322 | return -EFAULT; |
323 | 323 | ||
324 | err |= __get_user(temp.uint, &insn32->insn); | 324 | err |= __get_user(temp.uint, &insn32->insn); |
@@ -350,7 +350,7 @@ static int compat_insnlist(struct file *file, unsigned long arg) | |||
350 | insnlist32 = compat_ptr(arg); | 350 | insnlist32 = compat_ptr(arg); |
351 | 351 | ||
352 | /* Get 32-bit insnlist structure. */ | 352 | /* Get 32-bit insnlist structure. */ |
353 | if (!access_ok(VERIFY_READ, insnlist32, sizeof(*insnlist32))) | 353 | if (!access_ok(insnlist32, sizeof(*insnlist32))) |
354 | return -EFAULT; | 354 | return -EFAULT; |
355 | 355 | ||
356 | err = 0; | 356 | err = 0; |
@@ -365,7 +365,7 @@ static int compat_insnlist(struct file *file, unsigned long arg) | |||
365 | insn[n_insns])); | 365 | insn[n_insns])); |
366 | 366 | ||
367 | /* Set native insnlist structure. */ | 367 | /* Set native insnlist structure. */ |
368 | if (!access_ok(VERIFY_WRITE, &s->insnlist, sizeof(s->insnlist))) | 368 | if (!access_ok(&s->insnlist, sizeof(s->insnlist))) |
369 | return -EFAULT; | 369 | return -EFAULT; |
370 | 370 | ||
371 | err |= __put_user(n_insns, &s->insnlist.n_insns); | 371 | err |= __put_user(n_insns, &s->insnlist.n_insns); |
diff --git a/drivers/tty/n_hdlc.c b/drivers/tty/n_hdlc.c index 99460af61b77..4164414d4c64 100644 --- a/drivers/tty/n_hdlc.c +++ b/drivers/tty/n_hdlc.c | |||
@@ -573,7 +573,7 @@ static ssize_t n_hdlc_tty_read(struct tty_struct *tty, struct file *file, | |||
573 | return -EIO; | 573 | return -EIO; |
574 | 574 | ||
575 | /* verify user access to buffer */ | 575 | /* verify user access to buffer */ |
576 | if (!access_ok(VERIFY_WRITE, buf, nr)) { | 576 | if (!access_ok(buf, nr)) { |
577 | printk(KERN_WARNING "%s(%d) n_hdlc_tty_read() can't verify user " | 577 | printk(KERN_WARNING "%s(%d) n_hdlc_tty_read() can't verify user " |
578 | "buffer\n", __FILE__, __LINE__); | 578 | "buffer\n", __FILE__, __LINE__); |
579 | return -EFAULT; | 579 | return -EFAULT; |
diff --git a/drivers/usb/core/devices.c b/drivers/usb/core/devices.c index 3de3c750b5f6..44f28a114c2b 100644 --- a/drivers/usb/core/devices.c +++ b/drivers/usb/core/devices.c | |||
@@ -598,7 +598,7 @@ static ssize_t usb_device_read(struct file *file, char __user *buf, | |||
598 | return -EINVAL; | 598 | return -EINVAL; |
599 | if (nbytes <= 0) | 599 | if (nbytes <= 0) |
600 | return 0; | 600 | return 0; |
601 | if (!access_ok(VERIFY_WRITE, buf, nbytes)) | 601 | if (!access_ok(buf, nbytes)) |
602 | return -EFAULT; | 602 | return -EFAULT; |
603 | 603 | ||
604 | mutex_lock(&usb_bus_idr_lock); | 604 | mutex_lock(&usb_bus_idr_lock); |
diff --git a/drivers/usb/core/devio.c b/drivers/usb/core/devio.c index a75bc0b8a50f..d65566341dd1 100644 --- a/drivers/usb/core/devio.c +++ b/drivers/usb/core/devio.c | |||
@@ -1094,7 +1094,7 @@ static int proc_control(struct usb_dev_state *ps, void __user *arg) | |||
1094 | ctrl.bRequestType, ctrl.bRequest, ctrl.wValue, | 1094 | ctrl.bRequestType, ctrl.bRequest, ctrl.wValue, |
1095 | ctrl.wIndex, ctrl.wLength); | 1095 | ctrl.wIndex, ctrl.wLength); |
1096 | if (ctrl.bRequestType & 0x80) { | 1096 | if (ctrl.bRequestType & 0x80) { |
1097 | if (ctrl.wLength && !access_ok(VERIFY_WRITE, ctrl.data, | 1097 | if (ctrl.wLength && !access_ok(ctrl.data, |
1098 | ctrl.wLength)) { | 1098 | ctrl.wLength)) { |
1099 | ret = -EINVAL; | 1099 | ret = -EINVAL; |
1100 | goto done; | 1100 | goto done; |
@@ -1183,7 +1183,7 @@ static int proc_bulk(struct usb_dev_state *ps, void __user *arg) | |||
1183 | } | 1183 | } |
1184 | tmo = bulk.timeout; | 1184 | tmo = bulk.timeout; |
1185 | if (bulk.ep & 0x80) { | 1185 | if (bulk.ep & 0x80) { |
1186 | if (len1 && !access_ok(VERIFY_WRITE, bulk.data, len1)) { | 1186 | if (len1 && !access_ok(bulk.data, len1)) { |
1187 | ret = -EINVAL; | 1187 | ret = -EINVAL; |
1188 | goto done; | 1188 | goto done; |
1189 | } | 1189 | } |
@@ -1584,8 +1584,7 @@ static int proc_do_submiturb(struct usb_dev_state *ps, struct usbdevfs_urb *uurb | |||
1584 | } | 1584 | } |
1585 | 1585 | ||
1586 | if (uurb->buffer_length > 0 && | 1586 | if (uurb->buffer_length > 0 && |
1587 | !access_ok(is_in ? VERIFY_WRITE : VERIFY_READ, | 1587 | !access_ok(uurb->buffer, uurb->buffer_length)) { |
1588 | uurb->buffer, uurb->buffer_length)) { | ||
1589 | ret = -EFAULT; | 1588 | ret = -EFAULT; |
1590 | goto error; | 1589 | goto error; |
1591 | } | 1590 | } |
diff --git a/drivers/usb/gadget/function/f_hid.c b/drivers/usb/gadget/function/f_hid.c index 54e859dcb25c..75b113a5b25c 100644 --- a/drivers/usb/gadget/function/f_hid.c +++ b/drivers/usb/gadget/function/f_hid.c | |||
@@ -252,7 +252,7 @@ static ssize_t f_hidg_read(struct file *file, char __user *buffer, | |||
252 | if (!count) | 252 | if (!count) |
253 | return 0; | 253 | return 0; |
254 | 254 | ||
255 | if (!access_ok(VERIFY_WRITE, buffer, count)) | 255 | if (!access_ok(buffer, count)) |
256 | return -EFAULT; | 256 | return -EFAULT; |
257 | 257 | ||
258 | spin_lock_irqsave(&hidg->read_spinlock, flags); | 258 | spin_lock_irqsave(&hidg->read_spinlock, flags); |
@@ -339,7 +339,7 @@ static ssize_t f_hidg_write(struct file *file, const char __user *buffer, | |||
339 | unsigned long flags; | 339 | unsigned long flags; |
340 | ssize_t status = -ENOMEM; | 340 | ssize_t status = -ENOMEM; |
341 | 341 | ||
342 | if (!access_ok(VERIFY_READ, buffer, count)) | 342 | if (!access_ok(buffer, count)) |
343 | return -EFAULT; | 343 | return -EFAULT; |
344 | 344 | ||
345 | spin_lock_irqsave(&hidg->write_spinlock, flags); | 345 | spin_lock_irqsave(&hidg->write_spinlock, flags); |
diff --git a/drivers/usb/gadget/udc/atmel_usba_udc.c b/drivers/usb/gadget/udc/atmel_usba_udc.c index 11247322d587..660712e0bf98 100644 --- a/drivers/usb/gadget/udc/atmel_usba_udc.c +++ b/drivers/usb/gadget/udc/atmel_usba_udc.c | |||
@@ -88,7 +88,7 @@ static ssize_t queue_dbg_read(struct file *file, char __user *buf, | |||
88 | size_t len, remaining, actual = 0; | 88 | size_t len, remaining, actual = 0; |
89 | char tmpbuf[38]; | 89 | char tmpbuf[38]; |
90 | 90 | ||
91 | if (!access_ok(VERIFY_WRITE, buf, nbytes)) | 91 | if (!access_ok(buf, nbytes)) |
92 | return -EFAULT; | 92 | return -EFAULT; |
93 | 93 | ||
94 | inode_lock(file_inode(file)); | 94 | inode_lock(file_inode(file)); |
diff --git a/drivers/vhost/vhost.c b/drivers/vhost/vhost.c index 55e5aa662ad5..9f7942cbcbb2 100644 --- a/drivers/vhost/vhost.c +++ b/drivers/vhost/vhost.c | |||
@@ -655,7 +655,7 @@ static bool log_access_ok(void __user *log_base, u64 addr, unsigned long sz) | |||
655 | a + (unsigned long)log_base > ULONG_MAX) | 655 | a + (unsigned long)log_base > ULONG_MAX) |
656 | return false; | 656 | return false; |
657 | 657 | ||
658 | return access_ok(VERIFY_WRITE, log_base + a, | 658 | return access_ok(log_base + a, |
659 | (sz + VHOST_PAGE_SIZE * 8 - 1) / VHOST_PAGE_SIZE / 8); | 659 | (sz + VHOST_PAGE_SIZE * 8 - 1) / VHOST_PAGE_SIZE / 8); |
660 | } | 660 | } |
661 | 661 | ||
@@ -681,7 +681,7 @@ static bool vq_memory_access_ok(void __user *log_base, struct vhost_umem *umem, | |||
681 | return false; | 681 | return false; |
682 | 682 | ||
683 | 683 | ||
684 | if (!access_ok(VERIFY_WRITE, (void __user *)a, | 684 | if (!access_ok((void __user *)a, |
685 | node->size)) | 685 | node->size)) |
686 | return false; | 686 | return false; |
687 | else if (log_all && !log_access_ok(log_base, | 687 | else if (log_all && !log_access_ok(log_base, |
@@ -973,10 +973,10 @@ static bool umem_access_ok(u64 uaddr, u64 size, int access) | |||
973 | return false; | 973 | return false; |
974 | 974 | ||
975 | if ((access & VHOST_ACCESS_RO) && | 975 | if ((access & VHOST_ACCESS_RO) && |
976 | !access_ok(VERIFY_READ, (void __user *)a, size)) | 976 | !access_ok((void __user *)a, size)) |
977 | return false; | 977 | return false; |
978 | if ((access & VHOST_ACCESS_WO) && | 978 | if ((access & VHOST_ACCESS_WO) && |
979 | !access_ok(VERIFY_WRITE, (void __user *)a, size)) | 979 | !access_ok((void __user *)a, size)) |
980 | return false; | 980 | return false; |
981 | return true; | 981 | return true; |
982 | } | 982 | } |
@@ -1185,10 +1185,10 @@ static bool vq_access_ok(struct vhost_virtqueue *vq, unsigned int num, | |||
1185 | { | 1185 | { |
1186 | size_t s = vhost_has_feature(vq, VIRTIO_RING_F_EVENT_IDX) ? 2 : 0; | 1186 | size_t s = vhost_has_feature(vq, VIRTIO_RING_F_EVENT_IDX) ? 2 : 0; |
1187 | 1187 | ||
1188 | return access_ok(VERIFY_READ, desc, num * sizeof *desc) && | 1188 | return access_ok(desc, num * sizeof *desc) && |
1189 | access_ok(VERIFY_READ, avail, | 1189 | access_ok(avail, |
1190 | sizeof *avail + num * sizeof *avail->ring + s) && | 1190 | sizeof *avail + num * sizeof *avail->ring + s) && |
1191 | access_ok(VERIFY_WRITE, used, | 1191 | access_ok(used, |
1192 | sizeof *used + num * sizeof *used->ring + s); | 1192 | sizeof *used + num * sizeof *used->ring + s); |
1193 | } | 1193 | } |
1194 | 1194 | ||
@@ -1814,7 +1814,7 @@ int vhost_vq_init_access(struct vhost_virtqueue *vq) | |||
1814 | goto err; | 1814 | goto err; |
1815 | vq->signalled_used_valid = false; | 1815 | vq->signalled_used_valid = false; |
1816 | if (!vq->iotlb && | 1816 | if (!vq->iotlb && |
1817 | !access_ok(VERIFY_READ, &vq->used->idx, sizeof vq->used->idx)) { | 1817 | !access_ok(&vq->used->idx, sizeof vq->used->idx)) { |
1818 | r = -EFAULT; | 1818 | r = -EFAULT; |
1819 | goto err; | 1819 | goto err; |
1820 | } | 1820 | } |
diff --git a/drivers/video/fbdev/amifb.c b/drivers/video/fbdev/amifb.c index 0777aff211e5..758457026694 100644 --- a/drivers/video/fbdev/amifb.c +++ b/drivers/video/fbdev/amifb.c | |||
@@ -1855,7 +1855,7 @@ static int ami_get_var_cursorinfo(struct fb_var_cursorinfo *var, | |||
1855 | var->yspot = par->crsr.spot_y; | 1855 | var->yspot = par->crsr.spot_y; |
1856 | if (size > var->height * var->width) | 1856 | if (size > var->height * var->width) |
1857 | return -ENAMETOOLONG; | 1857 | return -ENAMETOOLONG; |
1858 | if (!access_ok(VERIFY_WRITE, data, size)) | 1858 | if (!access_ok(data, size)) |
1859 | return -EFAULT; | 1859 | return -EFAULT; |
1860 | delta = 1 << par->crsr.fmode; | 1860 | delta = 1 << par->crsr.fmode; |
1861 | lspr = lofsprite + (delta << 1); | 1861 | lspr = lofsprite + (delta << 1); |
@@ -1935,7 +1935,7 @@ static int ami_set_var_cursorinfo(struct fb_var_cursorinfo *var, | |||
1935 | return -EINVAL; | 1935 | return -EINVAL; |
1936 | if (!var->height) | 1936 | if (!var->height) |
1937 | return -EINVAL; | 1937 | return -EINVAL; |
1938 | if (!access_ok(VERIFY_READ, data, var->width * var->height)) | 1938 | if (!access_ok(data, var->width * var->height)) |
1939 | return -EFAULT; | 1939 | return -EFAULT; |
1940 | delta = 1 << fmode; | 1940 | delta = 1 << fmode; |
1941 | lofsprite = shfsprite = (u_short *)spritememory; | 1941 | lofsprite = shfsprite = (u_short *)spritememory; |
diff --git a/drivers/video/fbdev/omap2/omapfb/omapfb-ioctl.c b/drivers/video/fbdev/omap2/omapfb/omapfb-ioctl.c index a3edb20ea4c3..53f93616c671 100644 --- a/drivers/video/fbdev/omap2/omapfb/omapfb-ioctl.c +++ b/drivers/video/fbdev/omap2/omapfb/omapfb-ioctl.c | |||
@@ -493,7 +493,7 @@ static int omapfb_memory_read(struct fb_info *fbi, | |||
493 | if (!display || !display->driver->memory_read) | 493 | if (!display || !display->driver->memory_read) |
494 | return -ENOENT; | 494 | return -ENOENT; |
495 | 495 | ||
496 | if (!access_ok(VERIFY_WRITE, mr->buffer, mr->buffer_size)) | 496 | if (!access_ok(mr->buffer, mr->buffer_size)) |
497 | return -EFAULT; | 497 | return -EFAULT; |
498 | 498 | ||
499 | if (mr->w > 4096 || mr->h > 4096) | 499 | if (mr->w > 4096 || mr->h > 4096) |
diff --git a/drivers/xen/privcmd.c b/drivers/xen/privcmd.c index 7e6e682104dc..b24ddac1604b 100644 --- a/drivers/xen/privcmd.c +++ b/drivers/xen/privcmd.c | |||
@@ -459,14 +459,14 @@ static long privcmd_ioctl_mmap_batch( | |||
459 | return -EFAULT; | 459 | return -EFAULT; |
460 | /* Returns per-frame error in m.arr. */ | 460 | /* Returns per-frame error in m.arr. */ |
461 | m.err = NULL; | 461 | m.err = NULL; |
462 | if (!access_ok(VERIFY_WRITE, m.arr, m.num * sizeof(*m.arr))) | 462 | if (!access_ok(m.arr, m.num * sizeof(*m.arr))) |
463 | return -EFAULT; | 463 | return -EFAULT; |
464 | break; | 464 | break; |
465 | case 2: | 465 | case 2: |
466 | if (copy_from_user(&m, udata, sizeof(struct privcmd_mmapbatch_v2))) | 466 | if (copy_from_user(&m, udata, sizeof(struct privcmd_mmapbatch_v2))) |
467 | return -EFAULT; | 467 | return -EFAULT; |
468 | /* Returns per-frame error code in m.err. */ | 468 | /* Returns per-frame error code in m.err. */ |
469 | if (!access_ok(VERIFY_WRITE, m.err, m.num * (sizeof(*m.err)))) | 469 | if (!access_ok(m.err, m.num * (sizeof(*m.err)))) |
470 | return -EFAULT; | 470 | return -EFAULT; |
471 | break; | 471 | break; |
472 | default: | 472 | default: |
@@ -661,7 +661,7 @@ static long privcmd_ioctl_dm_op(struct file *file, void __user *udata) | |||
661 | goto out; | 661 | goto out; |
662 | } | 662 | } |
663 | 663 | ||
664 | if (!access_ok(VERIFY_WRITE, kbufs[i].uptr, | 664 | if (!access_ok(kbufs[i].uptr, |
665 | kbufs[i].size)) { | 665 | kbufs[i].size)) { |
666 | rc = -EFAULT; | 666 | rc = -EFAULT; |
667 | goto out; | 667 | goto out; |
diff --git a/fs/binfmt_aout.c b/fs/binfmt_aout.c index c3deb2e35f20..ca9725f18e00 100644 --- a/fs/binfmt_aout.c +++ b/fs/binfmt_aout.c | |||
@@ -78,9 +78,9 @@ static int aout_core_dump(struct coredump_params *cprm) | |||
78 | 78 | ||
79 | /* make sure we actually have a data and stack area to dump */ | 79 | /* make sure we actually have a data and stack area to dump */ |
80 | set_fs(USER_DS); | 80 | set_fs(USER_DS); |
81 | if (!access_ok(VERIFY_READ, START_DATA(dump), dump.u_dsize << PAGE_SHIFT)) | 81 | if (!access_ok(START_DATA(dump), dump.u_dsize << PAGE_SHIFT)) |
82 | dump.u_dsize = 0; | 82 | dump.u_dsize = 0; |
83 | if (!access_ok(VERIFY_READ, START_STACK(dump), dump.u_ssize << PAGE_SHIFT)) | 83 | if (!access_ok(START_STACK(dump), dump.u_ssize << PAGE_SHIFT)) |
84 | dump.u_ssize = 0; | 84 | dump.u_ssize = 0; |
85 | 85 | ||
86 | set_fs(KERNEL_DS); | 86 | set_fs(KERNEL_DS); |
diff --git a/fs/btrfs/send.c b/fs/btrfs/send.c index 1b15b43905f8..7ea2d6b1f170 100644 --- a/fs/btrfs/send.c +++ b/fs/btrfs/send.c | |||
@@ -6646,7 +6646,7 @@ long btrfs_ioctl_send(struct file *mnt_file, struct btrfs_ioctl_send_args *arg) | |||
6646 | goto out; | 6646 | goto out; |
6647 | } | 6647 | } |
6648 | 6648 | ||
6649 | if (!access_ok(VERIFY_READ, arg->clone_sources, | 6649 | if (!access_ok(arg->clone_sources, |
6650 | sizeof(*arg->clone_sources) * | 6650 | sizeof(*arg->clone_sources) * |
6651 | arg->clone_sources_count)) { | 6651 | arg->clone_sources_count)) { |
6652 | ret = -EFAULT; | 6652 | ret = -EFAULT; |
diff --git a/fs/eventpoll.c b/fs/eventpoll.c index 2329f96469e2..a5d219d920e7 100644 --- a/fs/eventpoll.c +++ b/fs/eventpoll.c | |||
@@ -2190,7 +2190,7 @@ static int do_epoll_wait(int epfd, struct epoll_event __user *events, | |||
2190 | return -EINVAL; | 2190 | return -EINVAL; |
2191 | 2191 | ||
2192 | /* Verify that the area passed by the user is writeable */ | 2192 | /* Verify that the area passed by the user is writeable */ |
2193 | if (!access_ok(VERIFY_WRITE, events, maxevents * sizeof(struct epoll_event))) | 2193 | if (!access_ok(events, maxevents * sizeof(struct epoll_event))) |
2194 | return -EFAULT; | 2194 | return -EFAULT; |
2195 | 2195 | ||
2196 | /* Get the "struct file *" for the eventpoll file */ | 2196 | /* Get the "struct file *" for the eventpoll file */ |
diff --git a/fs/fat/dir.c b/fs/fat/dir.c index 20acaea8a7e6..9d01db37183f 100644 --- a/fs/fat/dir.c +++ b/fs/fat/dir.c | |||
@@ -805,7 +805,7 @@ static long fat_dir_ioctl(struct file *filp, unsigned int cmd, | |||
805 | return fat_generic_ioctl(filp, cmd, arg); | 805 | return fat_generic_ioctl(filp, cmd, arg); |
806 | } | 806 | } |
807 | 807 | ||
808 | if (!access_ok(VERIFY_WRITE, d1, sizeof(struct __fat_dirent[2]))) | 808 | if (!access_ok(d1, sizeof(struct __fat_dirent[2]))) |
809 | return -EFAULT; | 809 | return -EFAULT; |
810 | /* | 810 | /* |
811 | * Yes, we don't need this put_user() absolutely. However old | 811 | * Yes, we don't need this put_user() absolutely. However old |
@@ -845,7 +845,7 @@ static long fat_compat_dir_ioctl(struct file *filp, unsigned cmd, | |||
845 | return fat_generic_ioctl(filp, cmd, (unsigned long)arg); | 845 | return fat_generic_ioctl(filp, cmd, (unsigned long)arg); |
846 | } | 846 | } |
847 | 847 | ||
848 | if (!access_ok(VERIFY_WRITE, d1, sizeof(struct compat_dirent[2]))) | 848 | if (!access_ok(d1, sizeof(struct compat_dirent[2]))) |
849 | return -EFAULT; | 849 | return -EFAULT; |
850 | /* | 850 | /* |
851 | * Yes, we don't need this put_user() absolutely. However old | 851 | * Yes, we don't need this put_user() absolutely. However old |
diff --git a/fs/ioctl.c b/fs/ioctl.c index d64f622cac8b..fef3a6bf7c78 100644 --- a/fs/ioctl.c +++ b/fs/ioctl.c | |||
@@ -203,7 +203,7 @@ static int ioctl_fiemap(struct file *filp, unsigned long arg) | |||
203 | fieinfo.fi_extents_start = ufiemap->fm_extents; | 203 | fieinfo.fi_extents_start = ufiemap->fm_extents; |
204 | 204 | ||
205 | if (fiemap.fm_extent_count != 0 && | 205 | if (fiemap.fm_extent_count != 0 && |
206 | !access_ok(VERIFY_WRITE, fieinfo.fi_extents_start, | 206 | !access_ok(fieinfo.fi_extents_start, |
207 | fieinfo.fi_extents_max * sizeof(struct fiemap_extent))) | 207 | fieinfo.fi_extents_max * sizeof(struct fiemap_extent))) |
208 | return -EFAULT; | 208 | return -EFAULT; |
209 | 209 | ||
diff --git a/fs/locks.c b/fs/locks.c index f0b24d98f36b..ff6af2c32601 100644 --- a/fs/locks.c +++ b/fs/locks.c | |||
@@ -453,7 +453,7 @@ static void locks_move_blocks(struct file_lock *new, struct file_lock *fl) | |||
453 | return; | 453 | return; |
454 | spin_lock(&blocked_lock_lock); | 454 | spin_lock(&blocked_lock_lock); |
455 | list_splice_init(&fl->fl_blocked_requests, &new->fl_blocked_requests); | 455 | list_splice_init(&fl->fl_blocked_requests, &new->fl_blocked_requests); |
456 | list_for_each_entry(f, &fl->fl_blocked_requests, fl_blocked_member) | 456 | list_for_each_entry(f, &new->fl_blocked_requests, fl_blocked_member) |
457 | f->fl_blocker = new; | 457 | f->fl_blocker = new; |
458 | spin_unlock(&blocked_lock_lock); | 458 | spin_unlock(&blocked_lock_lock); |
459 | } | 459 | } |
diff --git a/fs/namespace.c b/fs/namespace.c index a7f91265ea67..97b7c7098c3d 100644 --- a/fs/namespace.c +++ b/fs/namespace.c | |||
@@ -2651,7 +2651,7 @@ static long exact_copy_from_user(void *to, const void __user * from, | |||
2651 | const char __user *f = from; | 2651 | const char __user *f = from; |
2652 | char c; | 2652 | char c; |
2653 | 2653 | ||
2654 | if (!access_ok(VERIFY_READ, from, n)) | 2654 | if (!access_ok(from, n)) |
2655 | return n; | 2655 | return n; |
2656 | 2656 | ||
2657 | current->kernel_uaccess_faults_ok++; | 2657 | current->kernel_uaccess_faults_ok++; |
diff --git a/fs/ocfs2/dlmfs/dlmfs.c b/fs/ocfs2/dlmfs/dlmfs.c index b8fa1487cd85..8decbe95dcec 100644 --- a/fs/ocfs2/dlmfs/dlmfs.c +++ b/fs/ocfs2/dlmfs/dlmfs.c | |||
@@ -254,7 +254,7 @@ static ssize_t dlmfs_file_read(struct file *filp, | |||
254 | if (!count) | 254 | if (!count) |
255 | return 0; | 255 | return 0; |
256 | 256 | ||
257 | if (!access_ok(VERIFY_WRITE, buf, count)) | 257 | if (!access_ok(buf, count)) |
258 | return -EFAULT; | 258 | return -EFAULT; |
259 | 259 | ||
260 | /* don't read past the lvb */ | 260 | /* don't read past the lvb */ |
@@ -302,7 +302,7 @@ static ssize_t dlmfs_file_write(struct file *filp, | |||
302 | if (!count) | 302 | if (!count) |
303 | return 0; | 303 | return 0; |
304 | 304 | ||
305 | if (!access_ok(VERIFY_READ, buf, count)) | 305 | if (!access_ok(buf, count)) |
306 | return -EFAULT; | 306 | return -EFAULT; |
307 | 307 | ||
308 | /* don't write past the lvb */ | 308 | /* don't write past the lvb */ |
diff --git a/fs/pstore/pmsg.c b/fs/pstore/pmsg.c index 24db02de1787..97fcef74e5af 100644 --- a/fs/pstore/pmsg.c +++ b/fs/pstore/pmsg.c | |||
@@ -33,7 +33,7 @@ static ssize_t write_pmsg(struct file *file, const char __user *buf, | |||
33 | record.size = count; | 33 | record.size = count; |
34 | 34 | ||
35 | /* check outside lock, page in any data. write_user also checks */ | 35 | /* check outside lock, page in any data. write_user also checks */ |
36 | if (!access_ok(VERIFY_READ, buf, count)) | 36 | if (!access_ok(buf, count)) |
37 | return -EFAULT; | 37 | return -EFAULT; |
38 | 38 | ||
39 | mutex_lock(&pmsg_lock); | 39 | mutex_lock(&pmsg_lock); |
diff --git a/fs/pstore/ram_core.c b/fs/pstore/ram_core.c index c11711c2cc83..f375c0735351 100644 --- a/fs/pstore/ram_core.c +++ b/fs/pstore/ram_core.c | |||
@@ -357,7 +357,7 @@ int notrace persistent_ram_write_user(struct persistent_ram_zone *prz, | |||
357 | int rem, ret = 0, c = count; | 357 | int rem, ret = 0, c = count; |
358 | size_t start; | 358 | size_t start; |
359 | 359 | ||
360 | if (unlikely(!access_ok(VERIFY_READ, s, count))) | 360 | if (unlikely(!access_ok(s, count))) |
361 | return -EFAULT; | 361 | return -EFAULT; |
362 | if (unlikely(c > prz->buffer_size)) { | 362 | if (unlikely(c > prz->buffer_size)) { |
363 | s += c - prz->buffer_size; | 363 | s += c - prz->buffer_size; |
diff --git a/fs/read_write.c b/fs/read_write.c index 58f30537c47a..ff3c5e6f87cf 100644 --- a/fs/read_write.c +++ b/fs/read_write.c | |||
@@ -442,7 +442,7 @@ ssize_t vfs_read(struct file *file, char __user *buf, size_t count, loff_t *pos) | |||
442 | return -EBADF; | 442 | return -EBADF; |
443 | if (!(file->f_mode & FMODE_CAN_READ)) | 443 | if (!(file->f_mode & FMODE_CAN_READ)) |
444 | return -EINVAL; | 444 | return -EINVAL; |
445 | if (unlikely(!access_ok(VERIFY_WRITE, buf, count))) | 445 | if (unlikely(!access_ok(buf, count))) |
446 | return -EFAULT; | 446 | return -EFAULT; |
447 | 447 | ||
448 | ret = rw_verify_area(READ, file, pos, count); | 448 | ret = rw_verify_area(READ, file, pos, count); |
@@ -538,7 +538,7 @@ ssize_t vfs_write(struct file *file, const char __user *buf, size_t count, loff_ | |||
538 | return -EBADF; | 538 | return -EBADF; |
539 | if (!(file->f_mode & FMODE_CAN_WRITE)) | 539 | if (!(file->f_mode & FMODE_CAN_WRITE)) |
540 | return -EINVAL; | 540 | return -EINVAL; |
541 | if (unlikely(!access_ok(VERIFY_READ, buf, count))) | 541 | if (unlikely(!access_ok(buf, count))) |
542 | return -EFAULT; | 542 | return -EFAULT; |
543 | 543 | ||
544 | ret = rw_verify_area(WRITE, file, pos, count); | 544 | ret = rw_verify_area(WRITE, file, pos, count); |
@@ -718,9 +718,6 @@ static ssize_t do_loop_readv_writev(struct file *filp, struct iov_iter *iter, | |||
718 | return ret; | 718 | return ret; |
719 | } | 719 | } |
720 | 720 | ||
721 | /* A write operation does a read from user space and vice versa */ | ||
722 | #define vrfy_dir(type) ((type) == READ ? VERIFY_WRITE : VERIFY_READ) | ||
723 | |||
724 | /** | 721 | /** |
725 | * rw_copy_check_uvector() - Copy an array of &struct iovec from userspace | 722 | * rw_copy_check_uvector() - Copy an array of &struct iovec from userspace |
726 | * into the kernel and check that it is valid. | 723 | * into the kernel and check that it is valid. |
@@ -810,7 +807,7 @@ ssize_t rw_copy_check_uvector(int type, const struct iovec __user * uvector, | |||
810 | goto out; | 807 | goto out; |
811 | } | 808 | } |
812 | if (type >= 0 | 809 | if (type >= 0 |
813 | && unlikely(!access_ok(vrfy_dir(type), buf, len))) { | 810 | && unlikely(!access_ok(buf, len))) { |
814 | ret = -EFAULT; | 811 | ret = -EFAULT; |
815 | goto out; | 812 | goto out; |
816 | } | 813 | } |
@@ -856,7 +853,7 @@ ssize_t compat_rw_copy_check_uvector(int type, | |||
856 | *ret_pointer = iov; | 853 | *ret_pointer = iov; |
857 | 854 | ||
858 | ret = -EFAULT; | 855 | ret = -EFAULT; |
859 | if (!access_ok(VERIFY_READ, uvector, nr_segs*sizeof(*uvector))) | 856 | if (!access_ok(uvector, nr_segs*sizeof(*uvector))) |
860 | goto out; | 857 | goto out; |
861 | 858 | ||
862 | /* | 859 | /* |
@@ -881,7 +878,7 @@ ssize_t compat_rw_copy_check_uvector(int type, | |||
881 | if (len < 0) /* size_t not fitting in compat_ssize_t .. */ | 878 | if (len < 0) /* size_t not fitting in compat_ssize_t .. */ |
882 | goto out; | 879 | goto out; |
883 | if (type >= 0 && | 880 | if (type >= 0 && |
884 | !access_ok(vrfy_dir(type), compat_ptr(buf), len)) { | 881 | !access_ok(compat_ptr(buf), len)) { |
885 | ret = -EFAULT; | 882 | ret = -EFAULT; |
886 | goto out; | 883 | goto out; |
887 | } | 884 | } |
diff --git a/fs/readdir.c b/fs/readdir.c index d97f548e6323..2f6a4534e0df 100644 --- a/fs/readdir.c +++ b/fs/readdir.c | |||
@@ -105,7 +105,7 @@ static int fillonedir(struct dir_context *ctx, const char *name, int namlen, | |||
105 | } | 105 | } |
106 | buf->result++; | 106 | buf->result++; |
107 | dirent = buf->dirent; | 107 | dirent = buf->dirent; |
108 | if (!access_ok(VERIFY_WRITE, dirent, | 108 | if (!access_ok(dirent, |
109 | (unsigned long)(dirent->d_name + namlen + 1) - | 109 | (unsigned long)(dirent->d_name + namlen + 1) - |
110 | (unsigned long)dirent)) | 110 | (unsigned long)dirent)) |
111 | goto efault; | 111 | goto efault; |
@@ -221,7 +221,7 @@ SYSCALL_DEFINE3(getdents, unsigned int, fd, | |||
221 | }; | 221 | }; |
222 | int error; | 222 | int error; |
223 | 223 | ||
224 | if (!access_ok(VERIFY_WRITE, dirent, count)) | 224 | if (!access_ok(dirent, count)) |
225 | return -EFAULT; | 225 | return -EFAULT; |
226 | 226 | ||
227 | f = fdget_pos(fd); | 227 | f = fdget_pos(fd); |
@@ -304,7 +304,7 @@ int ksys_getdents64(unsigned int fd, struct linux_dirent64 __user *dirent, | |||
304 | }; | 304 | }; |
305 | int error; | 305 | int error; |
306 | 306 | ||
307 | if (!access_ok(VERIFY_WRITE, dirent, count)) | 307 | if (!access_ok(dirent, count)) |
308 | return -EFAULT; | 308 | return -EFAULT; |
309 | 309 | ||
310 | f = fdget_pos(fd); | 310 | f = fdget_pos(fd); |
@@ -365,7 +365,7 @@ static int compat_fillonedir(struct dir_context *ctx, const char *name, | |||
365 | } | 365 | } |
366 | buf->result++; | 366 | buf->result++; |
367 | dirent = buf->dirent; | 367 | dirent = buf->dirent; |
368 | if (!access_ok(VERIFY_WRITE, dirent, | 368 | if (!access_ok(dirent, |
369 | (unsigned long)(dirent->d_name + namlen + 1) - | 369 | (unsigned long)(dirent->d_name + namlen + 1) - |
370 | (unsigned long)dirent)) | 370 | (unsigned long)dirent)) |
371 | goto efault; | 371 | goto efault; |
@@ -475,7 +475,7 @@ COMPAT_SYSCALL_DEFINE3(getdents, unsigned int, fd, | |||
475 | }; | 475 | }; |
476 | int error; | 476 | int error; |
477 | 477 | ||
478 | if (!access_ok(VERIFY_WRITE, dirent, count)) | 478 | if (!access_ok(dirent, count)) |
479 | return -EFAULT; | 479 | return -EFAULT; |
480 | 480 | ||
481 | f = fdget_pos(fd); | 481 | f = fdget_pos(fd); |
diff --git a/fs/select.c b/fs/select.c index 4c8652390c94..d0f35dbc0e8f 100644 --- a/fs/select.c +++ b/fs/select.c | |||
@@ -381,9 +381,6 @@ typedef struct { | |||
381 | #define FDS_BYTES(nr) (FDS_LONGS(nr)*sizeof(long)) | 381 | #define FDS_BYTES(nr) (FDS_LONGS(nr)*sizeof(long)) |
382 | 382 | ||
383 | /* | 383 | /* |
384 | * We do a VERIFY_WRITE here even though we are only reading this time: | ||
385 | * we'll write to it eventually.. | ||
386 | * | ||
387 | * Use "unsigned long" accesses to let user-mode fd_set's be long-aligned. | 384 | * Use "unsigned long" accesses to let user-mode fd_set's be long-aligned. |
388 | */ | 385 | */ |
389 | static inline | 386 | static inline |
@@ -782,7 +779,7 @@ SYSCALL_DEFINE6(pselect6, int, n, fd_set __user *, inp, fd_set __user *, outp, | |||
782 | sigset_t __user *up = NULL; | 779 | sigset_t __user *up = NULL; |
783 | 780 | ||
784 | if (sig) { | 781 | if (sig) { |
785 | if (!access_ok(VERIFY_READ, sig, sizeof(void *)+sizeof(size_t)) | 782 | if (!access_ok(sig, sizeof(void *)+sizeof(size_t)) |
786 | || __get_user(up, (sigset_t __user * __user *)sig) | 783 | || __get_user(up, (sigset_t __user * __user *)sig) |
787 | || __get_user(sigsetsize, | 784 | || __get_user(sigsetsize, |
788 | (size_t __user *)(sig+sizeof(void *)))) | 785 | (size_t __user *)(sig+sizeof(void *)))) |
@@ -802,7 +799,7 @@ SYSCALL_DEFINE6(pselect6_time32, int, n, fd_set __user *, inp, fd_set __user *, | |||
802 | sigset_t __user *up = NULL; | 799 | sigset_t __user *up = NULL; |
803 | 800 | ||
804 | if (sig) { | 801 | if (sig) { |
805 | if (!access_ok(VERIFY_READ, sig, sizeof(void *)+sizeof(size_t)) | 802 | if (!access_ok(sig, sizeof(void *)+sizeof(size_t)) |
806 | || __get_user(up, (sigset_t __user * __user *)sig) | 803 | || __get_user(up, (sigset_t __user * __user *)sig) |
807 | || __get_user(sigsetsize, | 804 | || __get_user(sigsetsize, |
808 | (size_t __user *)(sig+sizeof(void *)))) | 805 | (size_t __user *)(sig+sizeof(void *)))) |
@@ -1368,7 +1365,7 @@ COMPAT_SYSCALL_DEFINE6(pselect6_time64, int, n, compat_ulong_t __user *, inp, | |||
1368 | compat_uptr_t up = 0; | 1365 | compat_uptr_t up = 0; |
1369 | 1366 | ||
1370 | if (sig) { | 1367 | if (sig) { |
1371 | if (!access_ok(VERIFY_READ, sig, | 1368 | if (!access_ok(sig, |
1372 | sizeof(compat_uptr_t)+sizeof(compat_size_t)) || | 1369 | sizeof(compat_uptr_t)+sizeof(compat_size_t)) || |
1373 | __get_user(up, (compat_uptr_t __user *)sig) || | 1370 | __get_user(up, (compat_uptr_t __user *)sig) || |
1374 | __get_user(sigsetsize, | 1371 | __get_user(sigsetsize, |
@@ -1390,7 +1387,7 @@ COMPAT_SYSCALL_DEFINE6(pselect6, int, n, compat_ulong_t __user *, inp, | |||
1390 | compat_uptr_t up = 0; | 1387 | compat_uptr_t up = 0; |
1391 | 1388 | ||
1392 | if (sig) { | 1389 | if (sig) { |
1393 | if (!access_ok(VERIFY_READ, sig, | 1390 | if (!access_ok(sig, |
1394 | sizeof(compat_uptr_t)+sizeof(compat_size_t)) || | 1391 | sizeof(compat_uptr_t)+sizeof(compat_size_t)) || |
1395 | __get_user(up, (compat_uptr_t __user *)sig) || | 1392 | __get_user(up, (compat_uptr_t __user *)sig) || |
1396 | __get_user(sigsetsize, | 1393 | __get_user(sigsetsize, |
diff --git a/include/asm-generic/uaccess.h b/include/asm-generic/uaccess.h index 6b2e63df2739..d82c78a79da5 100644 --- a/include/asm-generic/uaccess.h +++ b/include/asm-generic/uaccess.h | |||
@@ -35,7 +35,7 @@ static inline void set_fs(mm_segment_t fs) | |||
35 | #define segment_eq(a, b) ((a).seg == (b).seg) | 35 | #define segment_eq(a, b) ((a).seg == (b).seg) |
36 | #endif | 36 | #endif |
37 | 37 | ||
38 | #define access_ok(type, addr, size) __access_ok((unsigned long)(addr),(size)) | 38 | #define access_ok(addr, size) __access_ok((unsigned long)(addr),(size)) |
39 | 39 | ||
40 | /* | 40 | /* |
41 | * The architecture should really override this if possible, at least | 41 | * The architecture should really override this if possible, at least |
@@ -78,7 +78,7 @@ static inline int __access_ok(unsigned long addr, unsigned long size) | |||
78 | ({ \ | 78 | ({ \ |
79 | void __user *__p = (ptr); \ | 79 | void __user *__p = (ptr); \ |
80 | might_fault(); \ | 80 | might_fault(); \ |
81 | access_ok(VERIFY_WRITE, __p, sizeof(*ptr)) ? \ | 81 | access_ok(__p, sizeof(*ptr)) ? \ |
82 | __put_user((x), ((__typeof__(*(ptr)) __user *)__p)) : \ | 82 | __put_user((x), ((__typeof__(*(ptr)) __user *)__p)) : \ |
83 | -EFAULT; \ | 83 | -EFAULT; \ |
84 | }) | 84 | }) |
@@ -140,7 +140,7 @@ extern int __put_user_bad(void) __attribute__((noreturn)); | |||
140 | ({ \ | 140 | ({ \ |
141 | const void __user *__p = (ptr); \ | 141 | const void __user *__p = (ptr); \ |
142 | might_fault(); \ | 142 | might_fault(); \ |
143 | access_ok(VERIFY_READ, __p, sizeof(*ptr)) ? \ | 143 | access_ok(__p, sizeof(*ptr)) ? \ |
144 | __get_user((x), (__typeof__(*(ptr)) __user *)__p) :\ | 144 | __get_user((x), (__typeof__(*(ptr)) __user *)__p) :\ |
145 | ((x) = (__typeof__(*(ptr)))0,-EFAULT); \ | 145 | ((x) = (__typeof__(*(ptr)))0,-EFAULT); \ |
146 | }) | 146 | }) |
@@ -175,7 +175,7 @@ __strncpy_from_user(char *dst, const char __user *src, long count) | |||
175 | static inline long | 175 | static inline long |
176 | strncpy_from_user(char *dst, const char __user *src, long count) | 176 | strncpy_from_user(char *dst, const char __user *src, long count) |
177 | { | 177 | { |
178 | if (!access_ok(VERIFY_READ, src, 1)) | 178 | if (!access_ok(src, 1)) |
179 | return -EFAULT; | 179 | return -EFAULT; |
180 | return __strncpy_from_user(dst, src, count); | 180 | return __strncpy_from_user(dst, src, count); |
181 | } | 181 | } |
@@ -196,7 +196,7 @@ strncpy_from_user(char *dst, const char __user *src, long count) | |||
196 | */ | 196 | */ |
197 | static inline long strnlen_user(const char __user *src, long n) | 197 | static inline long strnlen_user(const char __user *src, long n) |
198 | { | 198 | { |
199 | if (!access_ok(VERIFY_READ, src, 1)) | 199 | if (!access_ok(src, 1)) |
200 | return 0; | 200 | return 0; |
201 | return __strnlen_user(src, n); | 201 | return __strnlen_user(src, n); |
202 | } | 202 | } |
@@ -217,7 +217,7 @@ static inline __must_check unsigned long | |||
217 | clear_user(void __user *to, unsigned long n) | 217 | clear_user(void __user *to, unsigned long n) |
218 | { | 218 | { |
219 | might_fault(); | 219 | might_fault(); |
220 | if (!access_ok(VERIFY_WRITE, to, n)) | 220 | if (!access_ok(to, n)) |
221 | return n; | 221 | return n; |
222 | 222 | ||
223 | return __clear_user(to, n); | 223 | return __clear_user(to, n); |
diff --git a/include/linux/bpf_verifier.h b/include/linux/bpf_verifier.h index c233efc106c6..27b74947cd2b 100644 --- a/include/linux/bpf_verifier.h +++ b/include/linux/bpf_verifier.h | |||
@@ -148,6 +148,7 @@ struct bpf_verifier_state { | |||
148 | /* call stack tracking */ | 148 | /* call stack tracking */ |
149 | struct bpf_func_state *frame[MAX_CALL_FRAMES]; | 149 | struct bpf_func_state *frame[MAX_CALL_FRAMES]; |
150 | u32 curframe; | 150 | u32 curframe; |
151 | bool speculative; | ||
151 | }; | 152 | }; |
152 | 153 | ||
153 | #define bpf_get_spilled_reg(slot, frame) \ | 154 | #define bpf_get_spilled_reg(slot, frame) \ |
@@ -167,15 +168,24 @@ struct bpf_verifier_state_list { | |||
167 | struct bpf_verifier_state_list *next; | 168 | struct bpf_verifier_state_list *next; |
168 | }; | 169 | }; |
169 | 170 | ||
171 | /* Possible states for alu_state member. */ | ||
172 | #define BPF_ALU_SANITIZE_SRC 1U | ||
173 | #define BPF_ALU_SANITIZE_DST 2U | ||
174 | #define BPF_ALU_NEG_VALUE (1U << 2) | ||
175 | #define BPF_ALU_SANITIZE (BPF_ALU_SANITIZE_SRC | \ | ||
176 | BPF_ALU_SANITIZE_DST) | ||
177 | |||
170 | struct bpf_insn_aux_data { | 178 | struct bpf_insn_aux_data { |
171 | union { | 179 | union { |
172 | enum bpf_reg_type ptr_type; /* pointer type for load/store insns */ | 180 | enum bpf_reg_type ptr_type; /* pointer type for load/store insns */ |
173 | unsigned long map_state; /* pointer/poison value for maps */ | 181 | unsigned long map_state; /* pointer/poison value for maps */ |
174 | s32 call_imm; /* saved imm field of call insn */ | 182 | s32 call_imm; /* saved imm field of call insn */ |
183 | u32 alu_limit; /* limit for add/sub register with pointer */ | ||
175 | }; | 184 | }; |
176 | int ctx_field_size; /* the ctx field size for load insn, maybe 0 */ | 185 | int ctx_field_size; /* the ctx field size for load insn, maybe 0 */ |
177 | int sanitize_stack_off; /* stack slot to be cleared */ | 186 | int sanitize_stack_off; /* stack slot to be cleared */ |
178 | bool seen; /* this insn was processed by the verifier */ | 187 | bool seen; /* this insn was processed by the verifier */ |
188 | u8 alu_state; /* used in combination with alu_limit */ | ||
179 | }; | 189 | }; |
180 | 190 | ||
181 | #define MAX_USED_MAPS 64 /* max number of maps accessed by one eBPF program */ | 191 | #define MAX_USED_MAPS 64 /* max number of maps accessed by one eBPF program */ |
@@ -212,6 +222,8 @@ struct bpf_subprog_info { | |||
212 | * one verifier_env per bpf_check() call | 222 | * one verifier_env per bpf_check() call |
213 | */ | 223 | */ |
214 | struct bpf_verifier_env { | 224 | struct bpf_verifier_env { |
225 | u32 insn_idx; | ||
226 | u32 prev_insn_idx; | ||
215 | struct bpf_prog *prog; /* eBPF program being verified */ | 227 | struct bpf_prog *prog; /* eBPF program being verified */ |
216 | const struct bpf_verifier_ops *ops; | 228 | const struct bpf_verifier_ops *ops; |
217 | struct bpf_verifier_stack_elem *head; /* stack of verifier states to be processed */ | 229 | struct bpf_verifier_stack_elem *head; /* stack of verifier states to be processed */ |
diff --git a/include/linux/filter.h b/include/linux/filter.h index 8c8544b375eb..ad106d845b22 100644 --- a/include/linux/filter.h +++ b/include/linux/filter.h | |||
@@ -53,14 +53,10 @@ struct sock_reuseport; | |||
53 | #define BPF_REG_D BPF_REG_8 /* data, callee-saved */ | 53 | #define BPF_REG_D BPF_REG_8 /* data, callee-saved */ |
54 | #define BPF_REG_H BPF_REG_9 /* hlen, callee-saved */ | 54 | #define BPF_REG_H BPF_REG_9 /* hlen, callee-saved */ |
55 | 55 | ||
56 | /* Kernel hidden auxiliary/helper register for hardening step. | 56 | /* Kernel hidden auxiliary/helper register. */ |
57 | * Only used by eBPF JITs. It's nothing more than a temporary | ||
58 | * register that JITs use internally, only that here it's part | ||
59 | * of eBPF instructions that have been rewritten for blinding | ||
60 | * constants. See JIT pre-step in bpf_jit_blind_constants(). | ||
61 | */ | ||
62 | #define BPF_REG_AX MAX_BPF_REG | 57 | #define BPF_REG_AX MAX_BPF_REG |
63 | #define MAX_BPF_JIT_REG (MAX_BPF_REG + 1) | 58 | #define MAX_BPF_EXT_REG (MAX_BPF_REG + 1) |
59 | #define MAX_BPF_JIT_REG MAX_BPF_EXT_REG | ||
64 | 60 | ||
65 | /* unused opcode to mark special call to bpf_tail_call() helper */ | 61 | /* unused opcode to mark special call to bpf_tail_call() helper */ |
66 | #define BPF_TAIL_CALL 0xf0 | 62 | #define BPF_TAIL_CALL 0xf0 |
diff --git a/include/linux/phy.h b/include/linux/phy.h index da039f211c22..3b051f761450 100644 --- a/include/linux/phy.h +++ b/include/linux/phy.h | |||
@@ -1,6 +1,6 @@ | |||
1 | /* | 1 | /* |
2 | * Framework and drivers for configuring and reading different PHYs | 2 | * Framework and drivers for configuring and reading different PHYs |
3 | * Based on code in sungem_phy.c and gianfar_phy.c | 3 | * Based on code in sungem_phy.c and (long-removed) gianfar_phy.c |
4 | * | 4 | * |
5 | * Author: Andy Fleming | 5 | * Author: Andy Fleming |
6 | * | 6 | * |
@@ -110,9 +110,9 @@ typedef enum { | |||
110 | * @speeds: buffer to store supported speeds in. | 110 | * @speeds: buffer to store supported speeds in. |
111 | * @size: size of speeds buffer. | 111 | * @size: size of speeds buffer. |
112 | * | 112 | * |
113 | * Description: Returns the number of supported speeds, and | 113 | * Description: Returns the number of supported speeds, and fills |
114 | * fills the speeds * buffer with the supported speeds. If speeds buffer is | 114 | * the speeds buffer with the supported speeds. If speeds buffer is |
115 | * too small to contain * all currently supported speeds, will return as | 115 | * too small to contain all currently supported speeds, will return as |
116 | * many speeds as can fit. | 116 | * many speeds as can fit. |
117 | */ | 117 | */ |
118 | unsigned int phy_supported_speeds(struct phy_device *phy, | 118 | unsigned int phy_supported_speeds(struct phy_device *phy, |
@@ -120,7 +120,10 @@ unsigned int phy_supported_speeds(struct phy_device *phy, | |||
120 | unsigned int size); | 120 | unsigned int size); |
121 | 121 | ||
122 | /** | 122 | /** |
123 | * It maps 'enum phy_interface_t' found in include/linux/phy.h | 123 | * phy_modes - map phy_interface_t enum to device tree binding of phy-mode |
124 | * @interface: enum phy_interface_t value | ||
125 | * | ||
126 | * Description: maps 'enum phy_interface_t' defined in this file | ||
124 | * into the device tree binding of 'phy-mode', so that Ethernet | 127 | * into the device tree binding of 'phy-mode', so that Ethernet |
125 | * device driver can get phy interface from device tree. | 128 | * device driver can get phy interface from device tree. |
126 | */ | 129 | */ |
diff --git a/include/linux/phy/phy.h b/include/linux/phy/phy.h index 1fdefadf150a..e8e118d70fd7 100644 --- a/include/linux/phy/phy.h +++ b/include/linux/phy/phy.h | |||
@@ -110,6 +110,7 @@ struct phy_ops { | |||
110 | /** | 110 | /** |
111 | * struct phy_attrs - represents phy attributes | 111 | * struct phy_attrs - represents phy attributes |
112 | * @bus_width: Data path width implemented by PHY | 112 | * @bus_width: Data path width implemented by PHY |
113 | * @mode: PHY mode | ||
113 | */ | 114 | */ |
114 | struct phy_attrs { | 115 | struct phy_attrs { |
115 | u32 bus_width; | 116 | u32 bus_width; |
@@ -121,7 +122,6 @@ struct phy_attrs { | |||
121 | * @dev: phy device | 122 | * @dev: phy device |
122 | * @id: id of the phy device | 123 | * @id: id of the phy device |
123 | * @ops: function pointers for performing phy operations | 124 | * @ops: function pointers for performing phy operations |
124 | * @init_data: list of PHY consumers (non-dt only) | ||
125 | * @mutex: mutex to protect phy_ops | 125 | * @mutex: mutex to protect phy_ops |
126 | * @init_count: used to protect when the PHY is used by multiple consumers | 126 | * @init_count: used to protect when the PHY is used by multiple consumers |
127 | * @power_count: used to protect when the PHY is used by multiple consumers | 127 | * @power_count: used to protect when the PHY is used by multiple consumers |
diff --git a/include/linux/ptr_ring.h b/include/linux/ptr_ring.h index 6894976b54e3..186cd8e970c7 100644 --- a/include/linux/ptr_ring.h +++ b/include/linux/ptr_ring.h | |||
@@ -573,6 +573,8 @@ static inline void **__ptr_ring_swap_queue(struct ptr_ring *r, void **queue, | |||
573 | else if (destroy) | 573 | else if (destroy) |
574 | destroy(ptr); | 574 | destroy(ptr); |
575 | 575 | ||
576 | if (producer >= size) | ||
577 | producer = 0; | ||
576 | __ptr_ring_set_size(r, size); | 578 | __ptr_ring_set_size(r, size); |
577 | r->producer = producer; | 579 | r->producer = producer; |
578 | r->consumer_head = 0; | 580 | r->consumer_head = 0; |
diff --git a/include/linux/regset.h b/include/linux/regset.h index 494cedaafdf2..a85c1707285c 100644 --- a/include/linux/regset.h +++ b/include/linux/regset.h | |||
@@ -376,7 +376,7 @@ static inline int copy_regset_to_user(struct task_struct *target, | |||
376 | if (!regset->get) | 376 | if (!regset->get) |
377 | return -EOPNOTSUPP; | 377 | return -EOPNOTSUPP; |
378 | 378 | ||
379 | if (!access_ok(VERIFY_WRITE, data, size)) | 379 | if (!access_ok(data, size)) |
380 | return -EFAULT; | 380 | return -EFAULT; |
381 | 381 | ||
382 | return regset->get(target, regset, offset, size, NULL, data); | 382 | return regset->get(target, regset, offset, size, NULL, data); |
@@ -402,7 +402,7 @@ static inline int copy_regset_from_user(struct task_struct *target, | |||
402 | if (!regset->set) | 402 | if (!regset->set) |
403 | return -EOPNOTSUPP; | 403 | return -EOPNOTSUPP; |
404 | 404 | ||
405 | if (!access_ok(VERIFY_READ, data, size)) | 405 | if (!access_ok(data, size)) |
406 | return -EFAULT; | 406 | return -EFAULT; |
407 | 407 | ||
408 | return regset->set(target, regset, offset, size, NULL, data); | 408 | return regset->set(target, regset, offset, size, NULL, data); |
diff --git a/include/linux/uaccess.h b/include/linux/uaccess.h index efe79c1cdd47..37b226e8df13 100644 --- a/include/linux/uaccess.h +++ b/include/linux/uaccess.h | |||
@@ -6,9 +6,6 @@ | |||
6 | #include <linux/thread_info.h> | 6 | #include <linux/thread_info.h> |
7 | #include <linux/kasan-checks.h> | 7 | #include <linux/kasan-checks.h> |
8 | 8 | ||
9 | #define VERIFY_READ 0 | ||
10 | #define VERIFY_WRITE 1 | ||
11 | |||
12 | #define uaccess_kernel() segment_eq(get_fs(), KERNEL_DS) | 9 | #define uaccess_kernel() segment_eq(get_fs(), KERNEL_DS) |
13 | 10 | ||
14 | #include <asm/uaccess.h> | 11 | #include <asm/uaccess.h> |
@@ -111,7 +108,7 @@ _copy_from_user(void *to, const void __user *from, unsigned long n) | |||
111 | { | 108 | { |
112 | unsigned long res = n; | 109 | unsigned long res = n; |
113 | might_fault(); | 110 | might_fault(); |
114 | if (likely(access_ok(VERIFY_READ, from, n))) { | 111 | if (likely(access_ok(from, n))) { |
115 | kasan_check_write(to, n); | 112 | kasan_check_write(to, n); |
116 | res = raw_copy_from_user(to, from, n); | 113 | res = raw_copy_from_user(to, from, n); |
117 | } | 114 | } |
@@ -129,7 +126,7 @@ static inline unsigned long | |||
129 | _copy_to_user(void __user *to, const void *from, unsigned long n) | 126 | _copy_to_user(void __user *to, const void *from, unsigned long n) |
130 | { | 127 | { |
131 | might_fault(); | 128 | might_fault(); |
132 | if (access_ok(VERIFY_WRITE, to, n)) { | 129 | if (access_ok(to, n)) { |
133 | kasan_check_read(from, n); | 130 | kasan_check_read(from, n); |
134 | n = raw_copy_to_user(to, from, n); | 131 | n = raw_copy_to_user(to, from, n); |
135 | } | 132 | } |
@@ -160,7 +157,7 @@ static __always_inline unsigned long __must_check | |||
160 | copy_in_user(void __user *to, const void __user *from, unsigned long n) | 157 | copy_in_user(void __user *to, const void __user *from, unsigned long n) |
161 | { | 158 | { |
162 | might_fault(); | 159 | might_fault(); |
163 | if (access_ok(VERIFY_WRITE, to, n) && access_ok(VERIFY_READ, from, n)) | 160 | if (access_ok(to, n) && access_ok(from, n)) |
164 | n = raw_copy_in_user(to, from, n); | 161 | n = raw_copy_in_user(to, from, n); |
165 | return n; | 162 | return n; |
166 | } | 163 | } |
@@ -267,7 +264,7 @@ extern long strncpy_from_unsafe(char *dst, const void *unsafe_addr, long count); | |||
267 | probe_kernel_read(&retval, addr, sizeof(retval)) | 264 | probe_kernel_read(&retval, addr, sizeof(retval)) |
268 | 265 | ||
269 | #ifndef user_access_begin | 266 | #ifndef user_access_begin |
270 | #define user_access_begin() do { } while (0) | 267 | #define user_access_begin(ptr,len) access_ok(ptr, len) |
271 | #define user_access_end() do { } while (0) | 268 | #define user_access_end() do { } while (0) |
272 | #define unsafe_get_user(x, ptr, err) do { if (unlikely(__get_user(x, ptr))) goto err; } while (0) | 269 | #define unsafe_get_user(x, ptr, err) do { if (unlikely(__get_user(x, ptr))) goto err; } while (0) |
273 | #define unsafe_put_user(x, ptr, err) do { if (unlikely(__put_user(x, ptr))) goto err; } while (0) | 270 | #define unsafe_put_user(x, ptr, err) do { if (unlikely(__put_user(x, ptr))) goto err; } while (0) |
diff --git a/include/net/checksum.h b/include/net/checksum.h index aef2b2bb6603..0f319e13be2c 100644 --- a/include/net/checksum.h +++ b/include/net/checksum.h | |||
@@ -30,7 +30,7 @@ static inline | |||
30 | __wsum csum_and_copy_from_user (const void __user *src, void *dst, | 30 | __wsum csum_and_copy_from_user (const void __user *src, void *dst, |
31 | int len, __wsum sum, int *err_ptr) | 31 | int len, __wsum sum, int *err_ptr) |
32 | { | 32 | { |
33 | if (access_ok(VERIFY_READ, src, len)) | 33 | if (access_ok(src, len)) |
34 | return csum_partial_copy_from_user(src, dst, len, sum, err_ptr); | 34 | return csum_partial_copy_from_user(src, dst, len, sum, err_ptr); |
35 | 35 | ||
36 | if (len) | 36 | if (len) |
@@ -46,7 +46,7 @@ static __inline__ __wsum csum_and_copy_to_user | |||
46 | { | 46 | { |
47 | sum = csum_partial(src, len, sum); | 47 | sum = csum_partial(src, len, sum); |
48 | 48 | ||
49 | if (access_ok(VERIFY_WRITE, dst, len)) { | 49 | if (access_ok(dst, len)) { |
50 | if (copy_to_user(dst, src, len) == 0) | 50 | if (copy_to_user(dst, src, len) == 0) |
51 | return sum; | 51 | return sum; |
52 | } | 52 | } |
diff --git a/include/net/ip_tunnels.h b/include/net/ip_tunnels.h index cbcf35ce1b14..34f019650941 100644 --- a/include/net/ip_tunnels.h +++ b/include/net/ip_tunnels.h | |||
@@ -308,6 +308,26 @@ int ip_tunnel_encap_del_ops(const struct ip_tunnel_encap_ops *op, | |||
308 | int ip_tunnel_encap_setup(struct ip_tunnel *t, | 308 | int ip_tunnel_encap_setup(struct ip_tunnel *t, |
309 | struct ip_tunnel_encap *ipencap); | 309 | struct ip_tunnel_encap *ipencap); |
310 | 310 | ||
311 | static inline bool pskb_inet_may_pull(struct sk_buff *skb) | ||
312 | { | ||
313 | int nhlen; | ||
314 | |||
315 | switch (skb->protocol) { | ||
316 | #if IS_ENABLED(CONFIG_IPV6) | ||
317 | case htons(ETH_P_IPV6): | ||
318 | nhlen = sizeof(struct ipv6hdr); | ||
319 | break; | ||
320 | #endif | ||
321 | case htons(ETH_P_IP): | ||
322 | nhlen = sizeof(struct iphdr); | ||
323 | break; | ||
324 | default: | ||
325 | nhlen = 0; | ||
326 | } | ||
327 | |||
328 | return pskb_network_may_pull(skb, nhlen); | ||
329 | } | ||
330 | |||
311 | static inline int ip_encap_hlen(struct ip_tunnel_encap *e) | 331 | static inline int ip_encap_hlen(struct ip_tunnel_encap *e) |
312 | { | 332 | { |
313 | const struct ip_tunnel_encap_ops *ops; | 333 | const struct ip_tunnel_encap_ops *ops; |
diff --git a/include/net/netfilter/nf_conntrack_count.h b/include/net/netfilter/nf_conntrack_count.h index 4b2b2baf8ab4..f32fc8289473 100644 --- a/include/net/netfilter/nf_conntrack_count.h +++ b/include/net/netfilter/nf_conntrack_count.h | |||
@@ -5,17 +5,10 @@ | |||
5 | 5 | ||
6 | struct nf_conncount_data; | 6 | struct nf_conncount_data; |
7 | 7 | ||
8 | enum nf_conncount_list_add { | ||
9 | NF_CONNCOUNT_ADDED, /* list add was ok */ | ||
10 | NF_CONNCOUNT_ERR, /* -ENOMEM, must drop skb */ | ||
11 | NF_CONNCOUNT_SKIP, /* list is already reclaimed by gc */ | ||
12 | }; | ||
13 | |||
14 | struct nf_conncount_list { | 8 | struct nf_conncount_list { |
15 | spinlock_t list_lock; | 9 | spinlock_t list_lock; |
16 | struct list_head head; /* connections with the same filtering key */ | 10 | struct list_head head; /* connections with the same filtering key */ |
17 | unsigned int count; /* length of list */ | 11 | unsigned int count; /* length of list */ |
18 | bool dead; | ||
19 | }; | 12 | }; |
20 | 13 | ||
21 | struct nf_conncount_data *nf_conncount_init(struct net *net, unsigned int family, | 14 | struct nf_conncount_data *nf_conncount_init(struct net *net, unsigned int family, |
@@ -29,18 +22,12 @@ unsigned int nf_conncount_count(struct net *net, | |||
29 | const struct nf_conntrack_tuple *tuple, | 22 | const struct nf_conntrack_tuple *tuple, |
30 | const struct nf_conntrack_zone *zone); | 23 | const struct nf_conntrack_zone *zone); |
31 | 24 | ||
32 | void nf_conncount_lookup(struct net *net, struct nf_conncount_list *list, | 25 | int nf_conncount_add(struct net *net, struct nf_conncount_list *list, |
33 | const struct nf_conntrack_tuple *tuple, | 26 | const struct nf_conntrack_tuple *tuple, |
34 | const struct nf_conntrack_zone *zone, | 27 | const struct nf_conntrack_zone *zone); |
35 | bool *addit); | ||
36 | 28 | ||
37 | void nf_conncount_list_init(struct nf_conncount_list *list); | 29 | void nf_conncount_list_init(struct nf_conncount_list *list); |
38 | 30 | ||
39 | enum nf_conncount_list_add | ||
40 | nf_conncount_add(struct nf_conncount_list *list, | ||
41 | const struct nf_conntrack_tuple *tuple, | ||
42 | const struct nf_conntrack_zone *zone); | ||
43 | |||
44 | bool nf_conncount_gc_list(struct net *net, | 31 | bool nf_conncount_gc_list(struct net *net, |
45 | struct nf_conncount_list *list); | 32 | struct nf_conncount_list *list); |
46 | 33 | ||
diff --git a/include/net/sock.h b/include/net/sock.h index a6235c286ef9..2b229f7be8eb 100644 --- a/include/net/sock.h +++ b/include/net/sock.h | |||
@@ -298,6 +298,7 @@ struct sock_common { | |||
298 | * @sk_filter: socket filtering instructions | 298 | * @sk_filter: socket filtering instructions |
299 | * @sk_timer: sock cleanup timer | 299 | * @sk_timer: sock cleanup timer |
300 | * @sk_stamp: time stamp of last packet received | 300 | * @sk_stamp: time stamp of last packet received |
301 | * @sk_stamp_seq: lock for accessing sk_stamp on 32 bit architectures only | ||
301 | * @sk_tsflags: SO_TIMESTAMPING socket options | 302 | * @sk_tsflags: SO_TIMESTAMPING socket options |
302 | * @sk_tskey: counter to disambiguate concurrent tstamp requests | 303 | * @sk_tskey: counter to disambiguate concurrent tstamp requests |
303 | * @sk_zckey: counter to order MSG_ZEROCOPY notifications | 304 | * @sk_zckey: counter to order MSG_ZEROCOPY notifications |
@@ -474,6 +475,9 @@ struct sock { | |||
474 | const struct cred *sk_peer_cred; | 475 | const struct cred *sk_peer_cred; |
475 | long sk_rcvtimeo; | 476 | long sk_rcvtimeo; |
476 | ktime_t sk_stamp; | 477 | ktime_t sk_stamp; |
478 | #if BITS_PER_LONG==32 | ||
479 | seqlock_t sk_stamp_seq; | ||
480 | #endif | ||
477 | u16 sk_tsflags; | 481 | u16 sk_tsflags; |
478 | u8 sk_shutdown; | 482 | u8 sk_shutdown; |
479 | u32 sk_tskey; | 483 | u32 sk_tskey; |
@@ -2297,6 +2301,34 @@ static inline void sk_drops_add(struct sock *sk, const struct sk_buff *skb) | |||
2297 | atomic_add(segs, &sk->sk_drops); | 2301 | atomic_add(segs, &sk->sk_drops); |
2298 | } | 2302 | } |
2299 | 2303 | ||
2304 | static inline ktime_t sock_read_timestamp(struct sock *sk) | ||
2305 | { | ||
2306 | #if BITS_PER_LONG==32 | ||
2307 | unsigned int seq; | ||
2308 | ktime_t kt; | ||
2309 | |||
2310 | do { | ||
2311 | seq = read_seqbegin(&sk->sk_stamp_seq); | ||
2312 | kt = sk->sk_stamp; | ||
2313 | } while (read_seqretry(&sk->sk_stamp_seq, seq)); | ||
2314 | |||
2315 | return kt; | ||
2316 | #else | ||
2317 | return sk->sk_stamp; | ||
2318 | #endif | ||
2319 | } | ||
2320 | |||
2321 | static inline void sock_write_timestamp(struct sock *sk, ktime_t kt) | ||
2322 | { | ||
2323 | #if BITS_PER_LONG==32 | ||
2324 | write_seqlock(&sk->sk_stamp_seq); | ||
2325 | sk->sk_stamp = kt; | ||
2326 | write_sequnlock(&sk->sk_stamp_seq); | ||
2327 | #else | ||
2328 | sk->sk_stamp = kt; | ||
2329 | #endif | ||
2330 | } | ||
2331 | |||
2300 | void __sock_recv_timestamp(struct msghdr *msg, struct sock *sk, | 2332 | void __sock_recv_timestamp(struct msghdr *msg, struct sock *sk, |
2301 | struct sk_buff *skb); | 2333 | struct sk_buff *skb); |
2302 | void __sock_recv_wifi_status(struct msghdr *msg, struct sock *sk, | 2334 | void __sock_recv_wifi_status(struct msghdr *msg, struct sock *sk, |
@@ -2321,7 +2353,7 @@ sock_recv_timestamp(struct msghdr *msg, struct sock *sk, struct sk_buff *skb) | |||
2321 | (sk->sk_tsflags & SOF_TIMESTAMPING_RAW_HARDWARE))) | 2353 | (sk->sk_tsflags & SOF_TIMESTAMPING_RAW_HARDWARE))) |
2322 | __sock_recv_timestamp(msg, sk, skb); | 2354 | __sock_recv_timestamp(msg, sk, skb); |
2323 | else | 2355 | else |
2324 | sk->sk_stamp = kt; | 2356 | sock_write_timestamp(sk, kt); |
2325 | 2357 | ||
2326 | if (sock_flag(sk, SOCK_WIFI_STATUS) && skb->wifi_acked_valid) | 2358 | if (sock_flag(sk, SOCK_WIFI_STATUS) && skb->wifi_acked_valid) |
2327 | __sock_recv_wifi_status(msg, sk, skb); | 2359 | __sock_recv_wifi_status(msg, sk, skb); |
@@ -2342,9 +2374,9 @@ static inline void sock_recv_ts_and_drops(struct msghdr *msg, struct sock *sk, | |||
2342 | if (sk->sk_flags & FLAGS_TS_OR_DROPS || sk->sk_tsflags & TSFLAGS_ANY) | 2374 | if (sk->sk_flags & FLAGS_TS_OR_DROPS || sk->sk_tsflags & TSFLAGS_ANY) |
2343 | __sock_recv_ts_and_drops(msg, sk, skb); | 2375 | __sock_recv_ts_and_drops(msg, sk, skb); |
2344 | else if (unlikely(sock_flag(sk, SOCK_TIMESTAMP))) | 2376 | else if (unlikely(sock_flag(sk, SOCK_TIMESTAMP))) |
2345 | sk->sk_stamp = skb->tstamp; | 2377 | sock_write_timestamp(sk, skb->tstamp); |
2346 | else if (unlikely(sk->sk_stamp == SK_DEFAULT_STAMP)) | 2378 | else if (unlikely(sk->sk_stamp == SK_DEFAULT_STAMP)) |
2347 | sk->sk_stamp = 0; | 2379 | sock_write_timestamp(sk, 0); |
2348 | } | 2380 | } |
2349 | 2381 | ||
2350 | void __sock_tx_timestamp(__u16 tsflags, __u8 *tx_flags); | 2382 | void __sock_tx_timestamp(__u16 tsflags, __u8 *tx_flags); |
diff --git a/kernel/bpf/core.c b/kernel/bpf/core.c index 38de580abcc2..f908b9356025 100644 --- a/kernel/bpf/core.c +++ b/kernel/bpf/core.c | |||
@@ -54,6 +54,7 @@ | |||
54 | #define DST regs[insn->dst_reg] | 54 | #define DST regs[insn->dst_reg] |
55 | #define SRC regs[insn->src_reg] | 55 | #define SRC regs[insn->src_reg] |
56 | #define FP regs[BPF_REG_FP] | 56 | #define FP regs[BPF_REG_FP] |
57 | #define AX regs[BPF_REG_AX] | ||
57 | #define ARG1 regs[BPF_REG_ARG1] | 58 | #define ARG1 regs[BPF_REG_ARG1] |
58 | #define CTX regs[BPF_REG_CTX] | 59 | #define CTX regs[BPF_REG_CTX] |
59 | #define IMM insn->imm | 60 | #define IMM insn->imm |
@@ -857,6 +858,26 @@ static int bpf_jit_blind_insn(const struct bpf_insn *from, | |||
857 | BUILD_BUG_ON(BPF_REG_AX + 1 != MAX_BPF_JIT_REG); | 858 | BUILD_BUG_ON(BPF_REG_AX + 1 != MAX_BPF_JIT_REG); |
858 | BUILD_BUG_ON(MAX_BPF_REG + 1 != MAX_BPF_JIT_REG); | 859 | BUILD_BUG_ON(MAX_BPF_REG + 1 != MAX_BPF_JIT_REG); |
859 | 860 | ||
861 | /* Constraints on AX register: | ||
862 | * | ||
863 | * AX register is inaccessible from user space. It is mapped in | ||
864 | * all JITs, and used here for constant blinding rewrites. It is | ||
865 | * typically "stateless" meaning its contents are only valid within | ||
866 | * the executed instruction, but not across several instructions. | ||
867 | * There are a few exceptions however which are further detailed | ||
868 | * below. | ||
869 | * | ||
870 | * Constant blinding is only used by JITs, not in the interpreter. | ||
871 | * The interpreter uses AX in some occasions as a local temporary | ||
872 | * register e.g. in DIV or MOD instructions. | ||
873 | * | ||
874 | * In restricted circumstances, the verifier can also use the AX | ||
875 | * register for rewrites as long as they do not interfere with | ||
876 | * the above cases! | ||
877 | */ | ||
878 | if (from->dst_reg == BPF_REG_AX || from->src_reg == BPF_REG_AX) | ||
879 | goto out; | ||
880 | |||
860 | if (from->imm == 0 && | 881 | if (from->imm == 0 && |
861 | (from->code == (BPF_ALU | BPF_MOV | BPF_K) || | 882 | (from->code == (BPF_ALU | BPF_MOV | BPF_K) || |
862 | from->code == (BPF_ALU64 | BPF_MOV | BPF_K))) { | 883 | from->code == (BPF_ALU64 | BPF_MOV | BPF_K))) { |
@@ -1188,7 +1209,6 @@ bool bpf_opcode_in_insntable(u8 code) | |||
1188 | */ | 1209 | */ |
1189 | static u64 ___bpf_prog_run(u64 *regs, const struct bpf_insn *insn, u64 *stack) | 1210 | static u64 ___bpf_prog_run(u64 *regs, const struct bpf_insn *insn, u64 *stack) |
1190 | { | 1211 | { |
1191 | u64 tmp; | ||
1192 | #define BPF_INSN_2_LBL(x, y) [BPF_##x | BPF_##y] = &&x##_##y | 1212 | #define BPF_INSN_2_LBL(x, y) [BPF_##x | BPF_##y] = &&x##_##y |
1193 | #define BPF_INSN_3_LBL(x, y, z) [BPF_##x | BPF_##y | BPF_##z] = &&x##_##y##_##z | 1213 | #define BPF_INSN_3_LBL(x, y, z) [BPF_##x | BPF_##y | BPF_##z] = &&x##_##y##_##z |
1194 | static const void *jumptable[256] = { | 1214 | static const void *jumptable[256] = { |
@@ -1268,36 +1288,36 @@ select_insn: | |||
1268 | (*(s64 *) &DST) >>= IMM; | 1288 | (*(s64 *) &DST) >>= IMM; |
1269 | CONT; | 1289 | CONT; |
1270 | ALU64_MOD_X: | 1290 | ALU64_MOD_X: |
1271 | div64_u64_rem(DST, SRC, &tmp); | 1291 | div64_u64_rem(DST, SRC, &AX); |
1272 | DST = tmp; | 1292 | DST = AX; |
1273 | CONT; | 1293 | CONT; |
1274 | ALU_MOD_X: | 1294 | ALU_MOD_X: |
1275 | tmp = (u32) DST; | 1295 | AX = (u32) DST; |
1276 | DST = do_div(tmp, (u32) SRC); | 1296 | DST = do_div(AX, (u32) SRC); |
1277 | CONT; | 1297 | CONT; |
1278 | ALU64_MOD_K: | 1298 | ALU64_MOD_K: |
1279 | div64_u64_rem(DST, IMM, &tmp); | 1299 | div64_u64_rem(DST, IMM, &AX); |
1280 | DST = tmp; | 1300 | DST = AX; |
1281 | CONT; | 1301 | CONT; |
1282 | ALU_MOD_K: | 1302 | ALU_MOD_K: |
1283 | tmp = (u32) DST; | 1303 | AX = (u32) DST; |
1284 | DST = do_div(tmp, (u32) IMM); | 1304 | DST = do_div(AX, (u32) IMM); |
1285 | CONT; | 1305 | CONT; |
1286 | ALU64_DIV_X: | 1306 | ALU64_DIV_X: |
1287 | DST = div64_u64(DST, SRC); | 1307 | DST = div64_u64(DST, SRC); |
1288 | CONT; | 1308 | CONT; |
1289 | ALU_DIV_X: | 1309 | ALU_DIV_X: |
1290 | tmp = (u32) DST; | 1310 | AX = (u32) DST; |
1291 | do_div(tmp, (u32) SRC); | 1311 | do_div(AX, (u32) SRC); |
1292 | DST = (u32) tmp; | 1312 | DST = (u32) AX; |
1293 | CONT; | 1313 | CONT; |
1294 | ALU64_DIV_K: | 1314 | ALU64_DIV_K: |
1295 | DST = div64_u64(DST, IMM); | 1315 | DST = div64_u64(DST, IMM); |
1296 | CONT; | 1316 | CONT; |
1297 | ALU_DIV_K: | 1317 | ALU_DIV_K: |
1298 | tmp = (u32) DST; | 1318 | AX = (u32) DST; |
1299 | do_div(tmp, (u32) IMM); | 1319 | do_div(AX, (u32) IMM); |
1300 | DST = (u32) tmp; | 1320 | DST = (u32) AX; |
1301 | CONT; | 1321 | CONT; |
1302 | ALU_END_TO_BE: | 1322 | ALU_END_TO_BE: |
1303 | switch (IMM) { | 1323 | switch (IMM) { |
@@ -1553,7 +1573,7 @@ STACK_FRAME_NON_STANDARD(___bpf_prog_run); /* jump table */ | |||
1553 | static unsigned int PROG_NAME(stack_size)(const void *ctx, const struct bpf_insn *insn) \ | 1573 | static unsigned int PROG_NAME(stack_size)(const void *ctx, const struct bpf_insn *insn) \ |
1554 | { \ | 1574 | { \ |
1555 | u64 stack[stack_size / sizeof(u64)]; \ | 1575 | u64 stack[stack_size / sizeof(u64)]; \ |
1556 | u64 regs[MAX_BPF_REG]; \ | 1576 | u64 regs[MAX_BPF_EXT_REG]; \ |
1557 | \ | 1577 | \ |
1558 | FP = (u64) (unsigned long) &stack[ARRAY_SIZE(stack)]; \ | 1578 | FP = (u64) (unsigned long) &stack[ARRAY_SIZE(stack)]; \ |
1559 | ARG1 = (u64) (unsigned long) ctx; \ | 1579 | ARG1 = (u64) (unsigned long) ctx; \ |
@@ -1566,7 +1586,7 @@ static u64 PROG_NAME_ARGS(stack_size)(u64 r1, u64 r2, u64 r3, u64 r4, u64 r5, \ | |||
1566 | const struct bpf_insn *insn) \ | 1586 | const struct bpf_insn *insn) \ |
1567 | { \ | 1587 | { \ |
1568 | u64 stack[stack_size / sizeof(u64)]; \ | 1588 | u64 stack[stack_size / sizeof(u64)]; \ |
1569 | u64 regs[MAX_BPF_REG]; \ | 1589 | u64 regs[MAX_BPF_EXT_REG]; \ |
1570 | \ | 1590 | \ |
1571 | FP = (u64) (unsigned long) &stack[ARRAY_SIZE(stack)]; \ | 1591 | FP = (u64) (unsigned long) &stack[ARRAY_SIZE(stack)]; \ |
1572 | BPF_R1 = r1; \ | 1592 | BPF_R1 = r1; \ |
diff --git a/kernel/bpf/syscall.c b/kernel/bpf/syscall.c index 0607db304def..b155cd17c1bd 100644 --- a/kernel/bpf/syscall.c +++ b/kernel/bpf/syscall.c | |||
@@ -79,7 +79,7 @@ int bpf_check_uarg_tail_zero(void __user *uaddr, | |||
79 | if (unlikely(actual_size > PAGE_SIZE)) /* silly large */ | 79 | if (unlikely(actual_size > PAGE_SIZE)) /* silly large */ |
80 | return -E2BIG; | 80 | return -E2BIG; |
81 | 81 | ||
82 | if (unlikely(!access_ok(VERIFY_READ, uaddr, actual_size))) | 82 | if (unlikely(!access_ok(uaddr, actual_size))) |
83 | return -EFAULT; | 83 | return -EFAULT; |
84 | 84 | ||
85 | if (actual_size <= expected_size) | 85 | if (actual_size <= expected_size) |
diff --git a/kernel/bpf/verifier.c b/kernel/bpf/verifier.c index 71d86e3024ae..f6bc62a9ee8e 100644 --- a/kernel/bpf/verifier.c +++ b/kernel/bpf/verifier.c | |||
@@ -710,6 +710,7 @@ static int copy_verifier_state(struct bpf_verifier_state *dst_state, | |||
710 | free_func_state(dst_state->frame[i]); | 710 | free_func_state(dst_state->frame[i]); |
711 | dst_state->frame[i] = NULL; | 711 | dst_state->frame[i] = NULL; |
712 | } | 712 | } |
713 | dst_state->speculative = src->speculative; | ||
713 | dst_state->curframe = src->curframe; | 714 | dst_state->curframe = src->curframe; |
714 | for (i = 0; i <= src->curframe; i++) { | 715 | for (i = 0; i <= src->curframe; i++) { |
715 | dst = dst_state->frame[i]; | 716 | dst = dst_state->frame[i]; |
@@ -754,7 +755,8 @@ static int pop_stack(struct bpf_verifier_env *env, int *prev_insn_idx, | |||
754 | } | 755 | } |
755 | 756 | ||
756 | static struct bpf_verifier_state *push_stack(struct bpf_verifier_env *env, | 757 | static struct bpf_verifier_state *push_stack(struct bpf_verifier_env *env, |
757 | int insn_idx, int prev_insn_idx) | 758 | int insn_idx, int prev_insn_idx, |
759 | bool speculative) | ||
758 | { | 760 | { |
759 | struct bpf_verifier_state *cur = env->cur_state; | 761 | struct bpf_verifier_state *cur = env->cur_state; |
760 | struct bpf_verifier_stack_elem *elem; | 762 | struct bpf_verifier_stack_elem *elem; |
@@ -772,6 +774,7 @@ static struct bpf_verifier_state *push_stack(struct bpf_verifier_env *env, | |||
772 | err = copy_verifier_state(&elem->st, cur); | 774 | err = copy_verifier_state(&elem->st, cur); |
773 | if (err) | 775 | if (err) |
774 | goto err; | 776 | goto err; |
777 | elem->st.speculative |= speculative; | ||
775 | if (env->stack_size > BPF_COMPLEXITY_LIMIT_STACK) { | 778 | if (env->stack_size > BPF_COMPLEXITY_LIMIT_STACK) { |
776 | verbose(env, "BPF program is too complex\n"); | 779 | verbose(env, "BPF program is too complex\n"); |
777 | goto err; | 780 | goto err; |
@@ -1387,6 +1390,31 @@ static int check_stack_read(struct bpf_verifier_env *env, | |||
1387 | } | 1390 | } |
1388 | } | 1391 | } |
1389 | 1392 | ||
1393 | static int check_stack_access(struct bpf_verifier_env *env, | ||
1394 | const struct bpf_reg_state *reg, | ||
1395 | int off, int size) | ||
1396 | { | ||
1397 | /* Stack accesses must be at a fixed offset, so that we | ||
1398 | * can determine what type of data were returned. See | ||
1399 | * check_stack_read(). | ||
1400 | */ | ||
1401 | if (!tnum_is_const(reg->var_off)) { | ||
1402 | char tn_buf[48]; | ||
1403 | |||
1404 | tnum_strn(tn_buf, sizeof(tn_buf), reg->var_off); | ||
1405 | verbose(env, "variable stack access var_off=%s off=%d size=%d", | ||
1406 | tn_buf, off, size); | ||
1407 | return -EACCES; | ||
1408 | } | ||
1409 | |||
1410 | if (off >= 0 || off < -MAX_BPF_STACK) { | ||
1411 | verbose(env, "invalid stack off=%d size=%d\n", off, size); | ||
1412 | return -EACCES; | ||
1413 | } | ||
1414 | |||
1415 | return 0; | ||
1416 | } | ||
1417 | |||
1390 | /* check read/write into map element returned by bpf_map_lookup_elem() */ | 1418 | /* check read/write into map element returned by bpf_map_lookup_elem() */ |
1391 | static int __check_map_access(struct bpf_verifier_env *env, u32 regno, int off, | 1419 | static int __check_map_access(struct bpf_verifier_env *env, u32 regno, int off, |
1392 | int size, bool zero_size_allowed) | 1420 | int size, bool zero_size_allowed) |
@@ -1418,13 +1446,17 @@ static int check_map_access(struct bpf_verifier_env *env, u32 regno, | |||
1418 | */ | 1446 | */ |
1419 | if (env->log.level) | 1447 | if (env->log.level) |
1420 | print_verifier_state(env, state); | 1448 | print_verifier_state(env, state); |
1449 | |||
1421 | /* The minimum value is only important with signed | 1450 | /* The minimum value is only important with signed |
1422 | * comparisons where we can't assume the floor of a | 1451 | * comparisons where we can't assume the floor of a |
1423 | * value is 0. If we are using signed variables for our | 1452 | * value is 0. If we are using signed variables for our |
1424 | * index'es we need to make sure that whatever we use | 1453 | * index'es we need to make sure that whatever we use |
1425 | * will have a set floor within our range. | 1454 | * will have a set floor within our range. |
1426 | */ | 1455 | */ |
1427 | if (reg->smin_value < 0) { | 1456 | if (reg->smin_value < 0 && |
1457 | (reg->smin_value == S64_MIN || | ||
1458 | (off + reg->smin_value != (s64)(s32)(off + reg->smin_value)) || | ||
1459 | reg->smin_value + off < 0)) { | ||
1428 | verbose(env, "R%d min value is negative, either use unsigned index or do a if (index >=0) check.\n", | 1460 | verbose(env, "R%d min value is negative, either use unsigned index or do a if (index >=0) check.\n", |
1429 | regno); | 1461 | regno); |
1430 | return -EACCES; | 1462 | return -EACCES; |
@@ -1954,24 +1986,10 @@ static int check_mem_access(struct bpf_verifier_env *env, int insn_idx, u32 regn | |||
1954 | } | 1986 | } |
1955 | 1987 | ||
1956 | } else if (reg->type == PTR_TO_STACK) { | 1988 | } else if (reg->type == PTR_TO_STACK) { |
1957 | /* stack accesses must be at a fixed offset, so that we can | ||
1958 | * determine what type of data were returned. | ||
1959 | * See check_stack_read(). | ||
1960 | */ | ||
1961 | if (!tnum_is_const(reg->var_off)) { | ||
1962 | char tn_buf[48]; | ||
1963 | |||
1964 | tnum_strn(tn_buf, sizeof(tn_buf), reg->var_off); | ||
1965 | verbose(env, "variable stack access var_off=%s off=%d size=%d", | ||
1966 | tn_buf, off, size); | ||
1967 | return -EACCES; | ||
1968 | } | ||
1969 | off += reg->var_off.value; | 1989 | off += reg->var_off.value; |
1970 | if (off >= 0 || off < -MAX_BPF_STACK) { | 1990 | err = check_stack_access(env, reg, off, size); |
1971 | verbose(env, "invalid stack off=%d size=%d\n", off, | 1991 | if (err) |
1972 | size); | 1992 | return err; |
1973 | return -EACCES; | ||
1974 | } | ||
1975 | 1993 | ||
1976 | state = func(env, reg); | 1994 | state = func(env, reg); |
1977 | err = update_stack_depth(env, state, off); | 1995 | err = update_stack_depth(env, state, off); |
@@ -3052,6 +3070,102 @@ static bool check_reg_sane_offset(struct bpf_verifier_env *env, | |||
3052 | return true; | 3070 | return true; |
3053 | } | 3071 | } |
3054 | 3072 | ||
3073 | static struct bpf_insn_aux_data *cur_aux(struct bpf_verifier_env *env) | ||
3074 | { | ||
3075 | return &env->insn_aux_data[env->insn_idx]; | ||
3076 | } | ||
3077 | |||
3078 | static int retrieve_ptr_limit(const struct bpf_reg_state *ptr_reg, | ||
3079 | u32 *ptr_limit, u8 opcode, bool off_is_neg) | ||
3080 | { | ||
3081 | bool mask_to_left = (opcode == BPF_ADD && off_is_neg) || | ||
3082 | (opcode == BPF_SUB && !off_is_neg); | ||
3083 | u32 off; | ||
3084 | |||
3085 | switch (ptr_reg->type) { | ||
3086 | case PTR_TO_STACK: | ||
3087 | off = ptr_reg->off + ptr_reg->var_off.value; | ||
3088 | if (mask_to_left) | ||
3089 | *ptr_limit = MAX_BPF_STACK + off; | ||
3090 | else | ||
3091 | *ptr_limit = -off; | ||
3092 | return 0; | ||
3093 | case PTR_TO_MAP_VALUE: | ||
3094 | if (mask_to_left) { | ||
3095 | *ptr_limit = ptr_reg->umax_value + ptr_reg->off; | ||
3096 | } else { | ||
3097 | off = ptr_reg->smin_value + ptr_reg->off; | ||
3098 | *ptr_limit = ptr_reg->map_ptr->value_size - off; | ||
3099 | } | ||
3100 | return 0; | ||
3101 | default: | ||
3102 | return -EINVAL; | ||
3103 | } | ||
3104 | } | ||
3105 | |||
3106 | static int sanitize_ptr_alu(struct bpf_verifier_env *env, | ||
3107 | struct bpf_insn *insn, | ||
3108 | const struct bpf_reg_state *ptr_reg, | ||
3109 | struct bpf_reg_state *dst_reg, | ||
3110 | bool off_is_neg) | ||
3111 | { | ||
3112 | struct bpf_verifier_state *vstate = env->cur_state; | ||
3113 | struct bpf_insn_aux_data *aux = cur_aux(env); | ||
3114 | bool ptr_is_dst_reg = ptr_reg == dst_reg; | ||
3115 | u8 opcode = BPF_OP(insn->code); | ||
3116 | u32 alu_state, alu_limit; | ||
3117 | struct bpf_reg_state tmp; | ||
3118 | bool ret; | ||
3119 | |||
3120 | if (env->allow_ptr_leaks || BPF_SRC(insn->code) == BPF_K) | ||
3121 | return 0; | ||
3122 | |||
3123 | /* We already marked aux for masking from non-speculative | ||
3124 | * paths, thus we got here in the first place. We only care | ||
3125 | * to explore bad access from here. | ||
3126 | */ | ||
3127 | if (vstate->speculative) | ||
3128 | goto do_sim; | ||
3129 | |||
3130 | alu_state = off_is_neg ? BPF_ALU_NEG_VALUE : 0; | ||
3131 | alu_state |= ptr_is_dst_reg ? | ||
3132 | BPF_ALU_SANITIZE_SRC : BPF_ALU_SANITIZE_DST; | ||
3133 | |||
3134 | if (retrieve_ptr_limit(ptr_reg, &alu_limit, opcode, off_is_neg)) | ||
3135 | return 0; | ||
3136 | |||
3137 | /* If we arrived here from different branches with different | ||
3138 | * limits to sanitize, then this won't work. | ||
3139 | */ | ||
3140 | if (aux->alu_state && | ||
3141 | (aux->alu_state != alu_state || | ||
3142 | aux->alu_limit != alu_limit)) | ||
3143 | return -EACCES; | ||
3144 | |||
3145 | /* Corresponding fixup done in fixup_bpf_calls(). */ | ||
3146 | aux->alu_state = alu_state; | ||
3147 | aux->alu_limit = alu_limit; | ||
3148 | |||
3149 | do_sim: | ||
3150 | /* Simulate and find potential out-of-bounds access under | ||
3151 | * speculative execution from truncation as a result of | ||
3152 | * masking when off was not within expected range. If off | ||
3153 | * sits in dst, then we temporarily need to move ptr there | ||
3154 | * to simulate dst (== 0) +/-= ptr. Needed, for example, | ||
3155 | * for cases where we use K-based arithmetic in one direction | ||
3156 | * and truncated reg-based in the other in order to explore | ||
3157 | * bad access. | ||
3158 | */ | ||
3159 | if (!ptr_is_dst_reg) { | ||
3160 | tmp = *dst_reg; | ||
3161 | *dst_reg = *ptr_reg; | ||
3162 | } | ||
3163 | ret = push_stack(env, env->insn_idx + 1, env->insn_idx, true); | ||
3164 | if (!ptr_is_dst_reg) | ||
3165 | *dst_reg = tmp; | ||
3166 | return !ret ? -EFAULT : 0; | ||
3167 | } | ||
3168 | |||
3055 | /* Handles arithmetic on a pointer and a scalar: computes new min/max and var_off. | 3169 | /* Handles arithmetic on a pointer and a scalar: computes new min/max and var_off. |
3056 | * Caller should also handle BPF_MOV case separately. | 3170 | * Caller should also handle BPF_MOV case separately. |
3057 | * If we return -EACCES, caller may want to try again treating pointer as a | 3171 | * If we return -EACCES, caller may want to try again treating pointer as a |
@@ -3070,8 +3184,9 @@ static int adjust_ptr_min_max_vals(struct bpf_verifier_env *env, | |||
3070 | smin_ptr = ptr_reg->smin_value, smax_ptr = ptr_reg->smax_value; | 3184 | smin_ptr = ptr_reg->smin_value, smax_ptr = ptr_reg->smax_value; |
3071 | u64 umin_val = off_reg->umin_value, umax_val = off_reg->umax_value, | 3185 | u64 umin_val = off_reg->umin_value, umax_val = off_reg->umax_value, |
3072 | umin_ptr = ptr_reg->umin_value, umax_ptr = ptr_reg->umax_value; | 3186 | umin_ptr = ptr_reg->umin_value, umax_ptr = ptr_reg->umax_value; |
3187 | u32 dst = insn->dst_reg, src = insn->src_reg; | ||
3073 | u8 opcode = BPF_OP(insn->code); | 3188 | u8 opcode = BPF_OP(insn->code); |
3074 | u32 dst = insn->dst_reg; | 3189 | int ret; |
3075 | 3190 | ||
3076 | dst_reg = ®s[dst]; | 3191 | dst_reg = ®s[dst]; |
3077 | 3192 | ||
@@ -3104,6 +3219,13 @@ static int adjust_ptr_min_max_vals(struct bpf_verifier_env *env, | |||
3104 | verbose(env, "R%d pointer arithmetic on %s prohibited\n", | 3219 | verbose(env, "R%d pointer arithmetic on %s prohibited\n", |
3105 | dst, reg_type_str[ptr_reg->type]); | 3220 | dst, reg_type_str[ptr_reg->type]); |
3106 | return -EACCES; | 3221 | return -EACCES; |
3222 | case PTR_TO_MAP_VALUE: | ||
3223 | if (!env->allow_ptr_leaks && !known && (smin_val < 0) != (smax_val < 0)) { | ||
3224 | verbose(env, "R%d has unknown scalar with mixed signed bounds, pointer arithmetic with it prohibited for !root\n", | ||
3225 | off_reg == dst_reg ? dst : src); | ||
3226 | return -EACCES; | ||
3227 | } | ||
3228 | /* fall-through */ | ||
3107 | default: | 3229 | default: |
3108 | break; | 3230 | break; |
3109 | } | 3231 | } |
@@ -3120,6 +3242,11 @@ static int adjust_ptr_min_max_vals(struct bpf_verifier_env *env, | |||
3120 | 3242 | ||
3121 | switch (opcode) { | 3243 | switch (opcode) { |
3122 | case BPF_ADD: | 3244 | case BPF_ADD: |
3245 | ret = sanitize_ptr_alu(env, insn, ptr_reg, dst_reg, smin_val < 0); | ||
3246 | if (ret < 0) { | ||
3247 | verbose(env, "R%d tried to add from different maps or paths\n", dst); | ||
3248 | return ret; | ||
3249 | } | ||
3123 | /* We can take a fixed offset as long as it doesn't overflow | 3250 | /* We can take a fixed offset as long as it doesn't overflow |
3124 | * the s32 'off' field | 3251 | * the s32 'off' field |
3125 | */ | 3252 | */ |
@@ -3170,6 +3297,11 @@ static int adjust_ptr_min_max_vals(struct bpf_verifier_env *env, | |||
3170 | } | 3297 | } |
3171 | break; | 3298 | break; |
3172 | case BPF_SUB: | 3299 | case BPF_SUB: |
3300 | ret = sanitize_ptr_alu(env, insn, ptr_reg, dst_reg, smin_val < 0); | ||
3301 | if (ret < 0) { | ||
3302 | verbose(env, "R%d tried to sub from different maps or paths\n", dst); | ||
3303 | return ret; | ||
3304 | } | ||
3173 | if (dst_reg == off_reg) { | 3305 | if (dst_reg == off_reg) { |
3174 | /* scalar -= pointer. Creates an unknown scalar */ | 3306 | /* scalar -= pointer. Creates an unknown scalar */ |
3175 | verbose(env, "R%d tried to subtract pointer from scalar\n", | 3307 | verbose(env, "R%d tried to subtract pointer from scalar\n", |
@@ -3249,6 +3381,25 @@ static int adjust_ptr_min_max_vals(struct bpf_verifier_env *env, | |||
3249 | __update_reg_bounds(dst_reg); | 3381 | __update_reg_bounds(dst_reg); |
3250 | __reg_deduce_bounds(dst_reg); | 3382 | __reg_deduce_bounds(dst_reg); |
3251 | __reg_bound_offset(dst_reg); | 3383 | __reg_bound_offset(dst_reg); |
3384 | |||
3385 | /* For unprivileged we require that resulting offset must be in bounds | ||
3386 | * in order to be able to sanitize access later on. | ||
3387 | */ | ||
3388 | if (!env->allow_ptr_leaks) { | ||
3389 | if (dst_reg->type == PTR_TO_MAP_VALUE && | ||
3390 | check_map_access(env, dst, dst_reg->off, 1, false)) { | ||
3391 | verbose(env, "R%d pointer arithmetic of map value goes out of range, " | ||
3392 | "prohibited for !root\n", dst); | ||
3393 | return -EACCES; | ||
3394 | } else if (dst_reg->type == PTR_TO_STACK && | ||
3395 | check_stack_access(env, dst_reg, dst_reg->off + | ||
3396 | dst_reg->var_off.value, 1)) { | ||
3397 | verbose(env, "R%d stack pointer arithmetic goes out of range, " | ||
3398 | "prohibited for !root\n", dst); | ||
3399 | return -EACCES; | ||
3400 | } | ||
3401 | } | ||
3402 | |||
3252 | return 0; | 3403 | return 0; |
3253 | } | 3404 | } |
3254 | 3405 | ||
@@ -4348,7 +4499,8 @@ static int check_cond_jmp_op(struct bpf_verifier_env *env, | |||
4348 | } | 4499 | } |
4349 | } | 4500 | } |
4350 | 4501 | ||
4351 | other_branch = push_stack(env, *insn_idx + insn->off + 1, *insn_idx); | 4502 | other_branch = push_stack(env, *insn_idx + insn->off + 1, *insn_idx, |
4503 | false); | ||
4352 | if (!other_branch) | 4504 | if (!other_branch) |
4353 | return -EFAULT; | 4505 | return -EFAULT; |
4354 | other_branch_regs = other_branch->frame[other_branch->curframe]->regs; | 4506 | other_branch_regs = other_branch->frame[other_branch->curframe]->regs; |
@@ -5458,6 +5610,12 @@ static bool states_equal(struct bpf_verifier_env *env, | |||
5458 | if (old->curframe != cur->curframe) | 5610 | if (old->curframe != cur->curframe) |
5459 | return false; | 5611 | return false; |
5460 | 5612 | ||
5613 | /* Verification state from speculative execution simulation | ||
5614 | * must never prune a non-speculative execution one. | ||
5615 | */ | ||
5616 | if (old->speculative && !cur->speculative) | ||
5617 | return false; | ||
5618 | |||
5461 | /* for states to be equal callsites have to be the same | 5619 | /* for states to be equal callsites have to be the same |
5462 | * and all frame states need to be equivalent | 5620 | * and all frame states need to be equivalent |
5463 | */ | 5621 | */ |
@@ -5650,7 +5808,6 @@ static int do_check(struct bpf_verifier_env *env) | |||
5650 | struct bpf_insn *insns = env->prog->insnsi; | 5808 | struct bpf_insn *insns = env->prog->insnsi; |
5651 | struct bpf_reg_state *regs; | 5809 | struct bpf_reg_state *regs; |
5652 | int insn_cnt = env->prog->len, i; | 5810 | int insn_cnt = env->prog->len, i; |
5653 | int insn_idx, prev_insn_idx = 0; | ||
5654 | int insn_processed = 0; | 5811 | int insn_processed = 0; |
5655 | bool do_print_state = false; | 5812 | bool do_print_state = false; |
5656 | 5813 | ||
@@ -5660,6 +5817,7 @@ static int do_check(struct bpf_verifier_env *env) | |||
5660 | if (!state) | 5817 | if (!state) |
5661 | return -ENOMEM; | 5818 | return -ENOMEM; |
5662 | state->curframe = 0; | 5819 | state->curframe = 0; |
5820 | state->speculative = false; | ||
5663 | state->frame[0] = kzalloc(sizeof(struct bpf_func_state), GFP_KERNEL); | 5821 | state->frame[0] = kzalloc(sizeof(struct bpf_func_state), GFP_KERNEL); |
5664 | if (!state->frame[0]) { | 5822 | if (!state->frame[0]) { |
5665 | kfree(state); | 5823 | kfree(state); |
@@ -5670,19 +5828,19 @@ static int do_check(struct bpf_verifier_env *env) | |||
5670 | BPF_MAIN_FUNC /* callsite */, | 5828 | BPF_MAIN_FUNC /* callsite */, |
5671 | 0 /* frameno */, | 5829 | 0 /* frameno */, |
5672 | 0 /* subprogno, zero == main subprog */); | 5830 | 0 /* subprogno, zero == main subprog */); |
5673 | insn_idx = 0; | 5831 | |
5674 | for (;;) { | 5832 | for (;;) { |
5675 | struct bpf_insn *insn; | 5833 | struct bpf_insn *insn; |
5676 | u8 class; | 5834 | u8 class; |
5677 | int err; | 5835 | int err; |
5678 | 5836 | ||
5679 | if (insn_idx >= insn_cnt) { | 5837 | if (env->insn_idx >= insn_cnt) { |
5680 | verbose(env, "invalid insn idx %d insn_cnt %d\n", | 5838 | verbose(env, "invalid insn idx %d insn_cnt %d\n", |
5681 | insn_idx, insn_cnt); | 5839 | env->insn_idx, insn_cnt); |
5682 | return -EFAULT; | 5840 | return -EFAULT; |
5683 | } | 5841 | } |
5684 | 5842 | ||
5685 | insn = &insns[insn_idx]; | 5843 | insn = &insns[env->insn_idx]; |
5686 | class = BPF_CLASS(insn->code); | 5844 | class = BPF_CLASS(insn->code); |
5687 | 5845 | ||
5688 | if (++insn_processed > BPF_COMPLEXITY_LIMIT_INSNS) { | 5846 | if (++insn_processed > BPF_COMPLEXITY_LIMIT_INSNS) { |
@@ -5692,17 +5850,19 @@ static int do_check(struct bpf_verifier_env *env) | |||
5692 | return -E2BIG; | 5850 | return -E2BIG; |
5693 | } | 5851 | } |
5694 | 5852 | ||
5695 | err = is_state_visited(env, insn_idx); | 5853 | err = is_state_visited(env, env->insn_idx); |
5696 | if (err < 0) | 5854 | if (err < 0) |
5697 | return err; | 5855 | return err; |
5698 | if (err == 1) { | 5856 | if (err == 1) { |
5699 | /* found equivalent state, can prune the search */ | 5857 | /* found equivalent state, can prune the search */ |
5700 | if (env->log.level) { | 5858 | if (env->log.level) { |
5701 | if (do_print_state) | 5859 | if (do_print_state) |
5702 | verbose(env, "\nfrom %d to %d: safe\n", | 5860 | verbose(env, "\nfrom %d to %d%s: safe\n", |
5703 | prev_insn_idx, insn_idx); | 5861 | env->prev_insn_idx, env->insn_idx, |
5862 | env->cur_state->speculative ? | ||
5863 | " (speculative execution)" : ""); | ||
5704 | else | 5864 | else |
5705 | verbose(env, "%d: safe\n", insn_idx); | 5865 | verbose(env, "%d: safe\n", env->insn_idx); |
5706 | } | 5866 | } |
5707 | goto process_bpf_exit; | 5867 | goto process_bpf_exit; |
5708 | } | 5868 | } |
@@ -5715,10 +5875,12 @@ static int do_check(struct bpf_verifier_env *env) | |||
5715 | 5875 | ||
5716 | if (env->log.level > 1 || (env->log.level && do_print_state)) { | 5876 | if (env->log.level > 1 || (env->log.level && do_print_state)) { |
5717 | if (env->log.level > 1) | 5877 | if (env->log.level > 1) |
5718 | verbose(env, "%d:", insn_idx); | 5878 | verbose(env, "%d:", env->insn_idx); |
5719 | else | 5879 | else |
5720 | verbose(env, "\nfrom %d to %d:", | 5880 | verbose(env, "\nfrom %d to %d%s:", |
5721 | prev_insn_idx, insn_idx); | 5881 | env->prev_insn_idx, env->insn_idx, |
5882 | env->cur_state->speculative ? | ||
5883 | " (speculative execution)" : ""); | ||
5722 | print_verifier_state(env, state->frame[state->curframe]); | 5884 | print_verifier_state(env, state->frame[state->curframe]); |
5723 | do_print_state = false; | 5885 | do_print_state = false; |
5724 | } | 5886 | } |
@@ -5729,20 +5891,20 @@ static int do_check(struct bpf_verifier_env *env) | |||
5729 | .private_data = env, | 5891 | .private_data = env, |
5730 | }; | 5892 | }; |
5731 | 5893 | ||
5732 | verbose_linfo(env, insn_idx, "; "); | 5894 | verbose_linfo(env, env->insn_idx, "; "); |
5733 | verbose(env, "%d: ", insn_idx); | 5895 | verbose(env, "%d: ", env->insn_idx); |
5734 | print_bpf_insn(&cbs, insn, env->allow_ptr_leaks); | 5896 | print_bpf_insn(&cbs, insn, env->allow_ptr_leaks); |
5735 | } | 5897 | } |
5736 | 5898 | ||
5737 | if (bpf_prog_is_dev_bound(env->prog->aux)) { | 5899 | if (bpf_prog_is_dev_bound(env->prog->aux)) { |
5738 | err = bpf_prog_offload_verify_insn(env, insn_idx, | 5900 | err = bpf_prog_offload_verify_insn(env, env->insn_idx, |
5739 | prev_insn_idx); | 5901 | env->prev_insn_idx); |
5740 | if (err) | 5902 | if (err) |
5741 | return err; | 5903 | return err; |
5742 | } | 5904 | } |
5743 | 5905 | ||
5744 | regs = cur_regs(env); | 5906 | regs = cur_regs(env); |
5745 | env->insn_aux_data[insn_idx].seen = true; | 5907 | env->insn_aux_data[env->insn_idx].seen = true; |
5746 | 5908 | ||
5747 | if (class == BPF_ALU || class == BPF_ALU64) { | 5909 | if (class == BPF_ALU || class == BPF_ALU64) { |
5748 | err = check_alu_op(env, insn); | 5910 | err = check_alu_op(env, insn); |
@@ -5768,13 +5930,13 @@ static int do_check(struct bpf_verifier_env *env) | |||
5768 | /* check that memory (src_reg + off) is readable, | 5930 | /* check that memory (src_reg + off) is readable, |
5769 | * the state of dst_reg will be updated by this func | 5931 | * the state of dst_reg will be updated by this func |
5770 | */ | 5932 | */ |
5771 | err = check_mem_access(env, insn_idx, insn->src_reg, insn->off, | 5933 | err = check_mem_access(env, env->insn_idx, insn->src_reg, |
5772 | BPF_SIZE(insn->code), BPF_READ, | 5934 | insn->off, BPF_SIZE(insn->code), |
5773 | insn->dst_reg, false); | 5935 | BPF_READ, insn->dst_reg, false); |
5774 | if (err) | 5936 | if (err) |
5775 | return err; | 5937 | return err; |
5776 | 5938 | ||
5777 | prev_src_type = &env->insn_aux_data[insn_idx].ptr_type; | 5939 | prev_src_type = &env->insn_aux_data[env->insn_idx].ptr_type; |
5778 | 5940 | ||
5779 | if (*prev_src_type == NOT_INIT) { | 5941 | if (*prev_src_type == NOT_INIT) { |
5780 | /* saw a valid insn | 5942 | /* saw a valid insn |
@@ -5799,10 +5961,10 @@ static int do_check(struct bpf_verifier_env *env) | |||
5799 | enum bpf_reg_type *prev_dst_type, dst_reg_type; | 5961 | enum bpf_reg_type *prev_dst_type, dst_reg_type; |
5800 | 5962 | ||
5801 | if (BPF_MODE(insn->code) == BPF_XADD) { | 5963 | if (BPF_MODE(insn->code) == BPF_XADD) { |
5802 | err = check_xadd(env, insn_idx, insn); | 5964 | err = check_xadd(env, env->insn_idx, insn); |
5803 | if (err) | 5965 | if (err) |
5804 | return err; | 5966 | return err; |
5805 | insn_idx++; | 5967 | env->insn_idx++; |
5806 | continue; | 5968 | continue; |
5807 | } | 5969 | } |
5808 | 5970 | ||
@@ -5818,13 +5980,13 @@ static int do_check(struct bpf_verifier_env *env) | |||
5818 | dst_reg_type = regs[insn->dst_reg].type; | 5980 | dst_reg_type = regs[insn->dst_reg].type; |
5819 | 5981 | ||
5820 | /* check that memory (dst_reg + off) is writeable */ | 5982 | /* check that memory (dst_reg + off) is writeable */ |
5821 | err = check_mem_access(env, insn_idx, insn->dst_reg, insn->off, | 5983 | err = check_mem_access(env, env->insn_idx, insn->dst_reg, |
5822 | BPF_SIZE(insn->code), BPF_WRITE, | 5984 | insn->off, BPF_SIZE(insn->code), |
5823 | insn->src_reg, false); | 5985 | BPF_WRITE, insn->src_reg, false); |
5824 | if (err) | 5986 | if (err) |
5825 | return err; | 5987 | return err; |
5826 | 5988 | ||
5827 | prev_dst_type = &env->insn_aux_data[insn_idx].ptr_type; | 5989 | prev_dst_type = &env->insn_aux_data[env->insn_idx].ptr_type; |
5828 | 5990 | ||
5829 | if (*prev_dst_type == NOT_INIT) { | 5991 | if (*prev_dst_type == NOT_INIT) { |
5830 | *prev_dst_type = dst_reg_type; | 5992 | *prev_dst_type = dst_reg_type; |
@@ -5852,9 +6014,9 @@ static int do_check(struct bpf_verifier_env *env) | |||
5852 | } | 6014 | } |
5853 | 6015 | ||
5854 | /* check that memory (dst_reg + off) is writeable */ | 6016 | /* check that memory (dst_reg + off) is writeable */ |
5855 | err = check_mem_access(env, insn_idx, insn->dst_reg, insn->off, | 6017 | err = check_mem_access(env, env->insn_idx, insn->dst_reg, |
5856 | BPF_SIZE(insn->code), BPF_WRITE, | 6018 | insn->off, BPF_SIZE(insn->code), |
5857 | -1, false); | 6019 | BPF_WRITE, -1, false); |
5858 | if (err) | 6020 | if (err) |
5859 | return err; | 6021 | return err; |
5860 | 6022 | ||
@@ -5872,9 +6034,9 @@ static int do_check(struct bpf_verifier_env *env) | |||
5872 | } | 6034 | } |
5873 | 6035 | ||
5874 | if (insn->src_reg == BPF_PSEUDO_CALL) | 6036 | if (insn->src_reg == BPF_PSEUDO_CALL) |
5875 | err = check_func_call(env, insn, &insn_idx); | 6037 | err = check_func_call(env, insn, &env->insn_idx); |
5876 | else | 6038 | else |
5877 | err = check_helper_call(env, insn->imm, insn_idx); | 6039 | err = check_helper_call(env, insn->imm, env->insn_idx); |
5878 | if (err) | 6040 | if (err) |
5879 | return err; | 6041 | return err; |
5880 | 6042 | ||
@@ -5887,7 +6049,7 @@ static int do_check(struct bpf_verifier_env *env) | |||
5887 | return -EINVAL; | 6049 | return -EINVAL; |
5888 | } | 6050 | } |
5889 | 6051 | ||
5890 | insn_idx += insn->off + 1; | 6052 | env->insn_idx += insn->off + 1; |
5891 | continue; | 6053 | continue; |
5892 | 6054 | ||
5893 | } else if (opcode == BPF_EXIT) { | 6055 | } else if (opcode == BPF_EXIT) { |
@@ -5901,8 +6063,8 @@ static int do_check(struct bpf_verifier_env *env) | |||
5901 | 6063 | ||
5902 | if (state->curframe) { | 6064 | if (state->curframe) { |
5903 | /* exit from nested function */ | 6065 | /* exit from nested function */ |
5904 | prev_insn_idx = insn_idx; | 6066 | env->prev_insn_idx = env->insn_idx; |
5905 | err = prepare_func_exit(env, &insn_idx); | 6067 | err = prepare_func_exit(env, &env->insn_idx); |
5906 | if (err) | 6068 | if (err) |
5907 | return err; | 6069 | return err; |
5908 | do_print_state = true; | 6070 | do_print_state = true; |
@@ -5932,7 +6094,8 @@ static int do_check(struct bpf_verifier_env *env) | |||
5932 | if (err) | 6094 | if (err) |
5933 | return err; | 6095 | return err; |
5934 | process_bpf_exit: | 6096 | process_bpf_exit: |
5935 | err = pop_stack(env, &prev_insn_idx, &insn_idx); | 6097 | err = pop_stack(env, &env->prev_insn_idx, |
6098 | &env->insn_idx); | ||
5936 | if (err < 0) { | 6099 | if (err < 0) { |
5937 | if (err != -ENOENT) | 6100 | if (err != -ENOENT) |
5938 | return err; | 6101 | return err; |
@@ -5942,7 +6105,7 @@ process_bpf_exit: | |||
5942 | continue; | 6105 | continue; |
5943 | } | 6106 | } |
5944 | } else { | 6107 | } else { |
5945 | err = check_cond_jmp_op(env, insn, &insn_idx); | 6108 | err = check_cond_jmp_op(env, insn, &env->insn_idx); |
5946 | if (err) | 6109 | if (err) |
5947 | return err; | 6110 | return err; |
5948 | } | 6111 | } |
@@ -5959,8 +6122,8 @@ process_bpf_exit: | |||
5959 | if (err) | 6122 | if (err) |
5960 | return err; | 6123 | return err; |
5961 | 6124 | ||
5962 | insn_idx++; | 6125 | env->insn_idx++; |
5963 | env->insn_aux_data[insn_idx].seen = true; | 6126 | env->insn_aux_data[env->insn_idx].seen = true; |
5964 | } else { | 6127 | } else { |
5965 | verbose(env, "invalid BPF_LD mode\n"); | 6128 | verbose(env, "invalid BPF_LD mode\n"); |
5966 | return -EINVAL; | 6129 | return -EINVAL; |
@@ -5970,7 +6133,7 @@ process_bpf_exit: | |||
5970 | return -EINVAL; | 6133 | return -EINVAL; |
5971 | } | 6134 | } |
5972 | 6135 | ||
5973 | insn_idx++; | 6136 | env->insn_idx++; |
5974 | } | 6137 | } |
5975 | 6138 | ||
5976 | verbose(env, "processed %d insns (limit %d), stack depth ", | 6139 | verbose(env, "processed %d insns (limit %d), stack depth ", |
@@ -6709,6 +6872,57 @@ static int fixup_bpf_calls(struct bpf_verifier_env *env) | |||
6709 | continue; | 6872 | continue; |
6710 | } | 6873 | } |
6711 | 6874 | ||
6875 | if (insn->code == (BPF_ALU64 | BPF_ADD | BPF_X) || | ||
6876 | insn->code == (BPF_ALU64 | BPF_SUB | BPF_X)) { | ||
6877 | const u8 code_add = BPF_ALU64 | BPF_ADD | BPF_X; | ||
6878 | const u8 code_sub = BPF_ALU64 | BPF_SUB | BPF_X; | ||
6879 | struct bpf_insn insn_buf[16]; | ||
6880 | struct bpf_insn *patch = &insn_buf[0]; | ||
6881 | bool issrc, isneg; | ||
6882 | u32 off_reg; | ||
6883 | |||
6884 | aux = &env->insn_aux_data[i + delta]; | ||
6885 | if (!aux->alu_state) | ||
6886 | continue; | ||
6887 | |||
6888 | isneg = aux->alu_state & BPF_ALU_NEG_VALUE; | ||
6889 | issrc = (aux->alu_state & BPF_ALU_SANITIZE) == | ||
6890 | BPF_ALU_SANITIZE_SRC; | ||
6891 | |||
6892 | off_reg = issrc ? insn->src_reg : insn->dst_reg; | ||
6893 | if (isneg) | ||
6894 | *patch++ = BPF_ALU64_IMM(BPF_MUL, off_reg, -1); | ||
6895 | *patch++ = BPF_MOV32_IMM(BPF_REG_AX, aux->alu_limit - 1); | ||
6896 | *patch++ = BPF_ALU64_REG(BPF_SUB, BPF_REG_AX, off_reg); | ||
6897 | *patch++ = BPF_ALU64_REG(BPF_OR, BPF_REG_AX, off_reg); | ||
6898 | *patch++ = BPF_ALU64_IMM(BPF_NEG, BPF_REG_AX, 0); | ||
6899 | *patch++ = BPF_ALU64_IMM(BPF_ARSH, BPF_REG_AX, 63); | ||
6900 | if (issrc) { | ||
6901 | *patch++ = BPF_ALU64_REG(BPF_AND, BPF_REG_AX, | ||
6902 | off_reg); | ||
6903 | insn->src_reg = BPF_REG_AX; | ||
6904 | } else { | ||
6905 | *patch++ = BPF_ALU64_REG(BPF_AND, off_reg, | ||
6906 | BPF_REG_AX); | ||
6907 | } | ||
6908 | if (isneg) | ||
6909 | insn->code = insn->code == code_add ? | ||
6910 | code_sub : code_add; | ||
6911 | *patch++ = *insn; | ||
6912 | if (issrc && isneg) | ||
6913 | *patch++ = BPF_ALU64_IMM(BPF_MUL, off_reg, -1); | ||
6914 | cnt = patch - insn_buf; | ||
6915 | |||
6916 | new_prog = bpf_patch_insn_data(env, i + delta, insn_buf, cnt); | ||
6917 | if (!new_prog) | ||
6918 | return -ENOMEM; | ||
6919 | |||
6920 | delta += cnt - 1; | ||
6921 | env->prog = prog = new_prog; | ||
6922 | insn = new_prog->insnsi + i + delta; | ||
6923 | continue; | ||
6924 | } | ||
6925 | |||
6712 | if (insn->code != (BPF_JMP | BPF_CALL)) | 6926 | if (insn->code != (BPF_JMP | BPF_CALL)) |
6713 | continue; | 6927 | continue; |
6714 | if (insn->src_reg == BPF_PSEUDO_CALL) | 6928 | if (insn->src_reg == BPF_PSEUDO_CALL) |
diff --git a/kernel/compat.c b/kernel/compat.c index 089d00d0da9c..f01affa17e22 100644 --- a/kernel/compat.c +++ b/kernel/compat.c | |||
@@ -95,28 +95,28 @@ int compat_put_timex(struct compat_timex __user *utp, const struct timex *txc) | |||
95 | 95 | ||
96 | static int __compat_get_timeval(struct timeval *tv, const struct old_timeval32 __user *ctv) | 96 | static int __compat_get_timeval(struct timeval *tv, const struct old_timeval32 __user *ctv) |
97 | { | 97 | { |
98 | return (!access_ok(VERIFY_READ, ctv, sizeof(*ctv)) || | 98 | return (!access_ok(ctv, sizeof(*ctv)) || |
99 | __get_user(tv->tv_sec, &ctv->tv_sec) || | 99 | __get_user(tv->tv_sec, &ctv->tv_sec) || |
100 | __get_user(tv->tv_usec, &ctv->tv_usec)) ? -EFAULT : 0; | 100 | __get_user(tv->tv_usec, &ctv->tv_usec)) ? -EFAULT : 0; |
101 | } | 101 | } |
102 | 102 | ||
103 | static int __compat_put_timeval(const struct timeval *tv, struct old_timeval32 __user *ctv) | 103 | static int __compat_put_timeval(const struct timeval *tv, struct old_timeval32 __user *ctv) |
104 | { | 104 | { |
105 | return (!access_ok(VERIFY_WRITE, ctv, sizeof(*ctv)) || | 105 | return (!access_ok(ctv, sizeof(*ctv)) || |
106 | __put_user(tv->tv_sec, &ctv->tv_sec) || | 106 | __put_user(tv->tv_sec, &ctv->tv_sec) || |
107 | __put_user(tv->tv_usec, &ctv->tv_usec)) ? -EFAULT : 0; | 107 | __put_user(tv->tv_usec, &ctv->tv_usec)) ? -EFAULT : 0; |
108 | } | 108 | } |
109 | 109 | ||
110 | static int __compat_get_timespec(struct timespec *ts, const struct old_timespec32 __user *cts) | 110 | static int __compat_get_timespec(struct timespec *ts, const struct old_timespec32 __user *cts) |
111 | { | 111 | { |
112 | return (!access_ok(VERIFY_READ, cts, sizeof(*cts)) || | 112 | return (!access_ok(cts, sizeof(*cts)) || |
113 | __get_user(ts->tv_sec, &cts->tv_sec) || | 113 | __get_user(ts->tv_sec, &cts->tv_sec) || |
114 | __get_user(ts->tv_nsec, &cts->tv_nsec)) ? -EFAULT : 0; | 114 | __get_user(ts->tv_nsec, &cts->tv_nsec)) ? -EFAULT : 0; |
115 | } | 115 | } |
116 | 116 | ||
117 | static int __compat_put_timespec(const struct timespec *ts, struct old_timespec32 __user *cts) | 117 | static int __compat_put_timespec(const struct timespec *ts, struct old_timespec32 __user *cts) |
118 | { | 118 | { |
119 | return (!access_ok(VERIFY_WRITE, cts, sizeof(*cts)) || | 119 | return (!access_ok(cts, sizeof(*cts)) || |
120 | __put_user(ts->tv_sec, &cts->tv_sec) || | 120 | __put_user(ts->tv_sec, &cts->tv_sec) || |
121 | __put_user(ts->tv_nsec, &cts->tv_nsec)) ? -EFAULT : 0; | 121 | __put_user(ts->tv_nsec, &cts->tv_nsec)) ? -EFAULT : 0; |
122 | } | 122 | } |
@@ -335,7 +335,7 @@ int get_compat_sigevent(struct sigevent *event, | |||
335 | const struct compat_sigevent __user *u_event) | 335 | const struct compat_sigevent __user *u_event) |
336 | { | 336 | { |
337 | memset(event, 0, sizeof(*event)); | 337 | memset(event, 0, sizeof(*event)); |
338 | return (!access_ok(VERIFY_READ, u_event, sizeof(*u_event)) || | 338 | return (!access_ok(u_event, sizeof(*u_event)) || |
339 | __get_user(event->sigev_value.sival_int, | 339 | __get_user(event->sigev_value.sival_int, |
340 | &u_event->sigev_value.sival_int) || | 340 | &u_event->sigev_value.sival_int) || |
341 | __get_user(event->sigev_signo, &u_event->sigev_signo) || | 341 | __get_user(event->sigev_signo, &u_event->sigev_signo) || |
@@ -354,10 +354,9 @@ long compat_get_bitmap(unsigned long *mask, const compat_ulong_t __user *umask, | |||
354 | bitmap_size = ALIGN(bitmap_size, BITS_PER_COMPAT_LONG); | 354 | bitmap_size = ALIGN(bitmap_size, BITS_PER_COMPAT_LONG); |
355 | nr_compat_longs = BITS_TO_COMPAT_LONGS(bitmap_size); | 355 | nr_compat_longs = BITS_TO_COMPAT_LONGS(bitmap_size); |
356 | 356 | ||
357 | if (!access_ok(VERIFY_READ, umask, bitmap_size / 8)) | 357 | if (!user_access_begin(umask, bitmap_size / 8)) |
358 | return -EFAULT; | 358 | return -EFAULT; |
359 | 359 | ||
360 | user_access_begin(); | ||
361 | while (nr_compat_longs > 1) { | 360 | while (nr_compat_longs > 1) { |
362 | compat_ulong_t l1, l2; | 361 | compat_ulong_t l1, l2; |
363 | unsafe_get_user(l1, umask++, Efault); | 362 | unsafe_get_user(l1, umask++, Efault); |
@@ -384,10 +383,9 @@ long compat_put_bitmap(compat_ulong_t __user *umask, unsigned long *mask, | |||
384 | bitmap_size = ALIGN(bitmap_size, BITS_PER_COMPAT_LONG); | 383 | bitmap_size = ALIGN(bitmap_size, BITS_PER_COMPAT_LONG); |
385 | nr_compat_longs = BITS_TO_COMPAT_LONGS(bitmap_size); | 384 | nr_compat_longs = BITS_TO_COMPAT_LONGS(bitmap_size); |
386 | 385 | ||
387 | if (!access_ok(VERIFY_WRITE, umask, bitmap_size / 8)) | 386 | if (!user_access_begin(umask, bitmap_size / 8)) |
388 | return -EFAULT; | 387 | return -EFAULT; |
389 | 388 | ||
390 | user_access_begin(); | ||
391 | while (nr_compat_longs > 1) { | 389 | while (nr_compat_longs > 1) { |
392 | unsigned long m = *mask++; | 390 | unsigned long m = *mask++; |
393 | unsafe_put_user((compat_ulong_t)m, umask++, Efault); | 391 | unsafe_put_user((compat_ulong_t)m, umask++, Efault); |
@@ -438,7 +436,7 @@ void __user *compat_alloc_user_space(unsigned long len) | |||
438 | 436 | ||
439 | ptr = arch_compat_alloc_user_space(len); | 437 | ptr = arch_compat_alloc_user_space(len); |
440 | 438 | ||
441 | if (unlikely(!access_ok(VERIFY_WRITE, ptr, len))) | 439 | if (unlikely(!access_ok(ptr, len))) |
442 | return NULL; | 440 | return NULL; |
443 | 441 | ||
444 | return ptr; | 442 | return ptr; |
diff --git a/kernel/events/core.c b/kernel/events/core.c index 67ecac337374..3cd13a30f732 100644 --- a/kernel/events/core.c +++ b/kernel/events/core.c | |||
@@ -10135,7 +10135,7 @@ static int perf_copy_attr(struct perf_event_attr __user *uattr, | |||
10135 | u32 size; | 10135 | u32 size; |
10136 | int ret; | 10136 | int ret; |
10137 | 10137 | ||
10138 | if (!access_ok(VERIFY_WRITE, uattr, PERF_ATTR_SIZE_VER0)) | 10138 | if (!access_ok(uattr, PERF_ATTR_SIZE_VER0)) |
10139 | return -EFAULT; | 10139 | return -EFAULT; |
10140 | 10140 | ||
10141 | /* | 10141 | /* |
diff --git a/kernel/exit.c b/kernel/exit.c index 0e21e6d21f35..2d14979577ee 100644 --- a/kernel/exit.c +++ b/kernel/exit.c | |||
@@ -1604,10 +1604,9 @@ SYSCALL_DEFINE5(waitid, int, which, pid_t, upid, struct siginfo __user *, | |||
1604 | if (!infop) | 1604 | if (!infop) |
1605 | return err; | 1605 | return err; |
1606 | 1606 | ||
1607 | if (!access_ok(VERIFY_WRITE, infop, sizeof(*infop))) | 1607 | if (!user_access_begin(infop, sizeof(*infop))) |
1608 | return -EFAULT; | 1608 | return -EFAULT; |
1609 | 1609 | ||
1610 | user_access_begin(); | ||
1611 | unsafe_put_user(signo, &infop->si_signo, Efault); | 1610 | unsafe_put_user(signo, &infop->si_signo, Efault); |
1612 | unsafe_put_user(0, &infop->si_errno, Efault); | 1611 | unsafe_put_user(0, &infop->si_errno, Efault); |
1613 | unsafe_put_user(info.cause, &infop->si_code, Efault); | 1612 | unsafe_put_user(info.cause, &infop->si_code, Efault); |
@@ -1732,10 +1731,9 @@ COMPAT_SYSCALL_DEFINE5(waitid, | |||
1732 | if (!infop) | 1731 | if (!infop) |
1733 | return err; | 1732 | return err; |
1734 | 1733 | ||
1735 | if (!access_ok(VERIFY_WRITE, infop, sizeof(*infop))) | 1734 | if (!user_access_begin(infop, sizeof(*infop))) |
1736 | return -EFAULT; | 1735 | return -EFAULT; |
1737 | 1736 | ||
1738 | user_access_begin(); | ||
1739 | unsafe_put_user(signo, &infop->si_signo, Efault); | 1737 | unsafe_put_user(signo, &infop->si_signo, Efault); |
1740 | unsafe_put_user(0, &infop->si_errno, Efault); | 1738 | unsafe_put_user(0, &infop->si_errno, Efault); |
1741 | unsafe_put_user(info.cause, &infop->si_code, Efault); | 1739 | unsafe_put_user(info.cause, &infop->si_code, Efault); |
diff --git a/kernel/futex.c b/kernel/futex.c index 054105854e0e..be3bff2315ff 100644 --- a/kernel/futex.c +++ b/kernel/futex.c | |||
@@ -481,13 +481,18 @@ static void drop_futex_key_refs(union futex_key *key) | |||
481 | } | 481 | } |
482 | } | 482 | } |
483 | 483 | ||
484 | enum futex_access { | ||
485 | FUTEX_READ, | ||
486 | FUTEX_WRITE | ||
487 | }; | ||
488 | |||
484 | /** | 489 | /** |
485 | * get_futex_key() - Get parameters which are the keys for a futex | 490 | * get_futex_key() - Get parameters which are the keys for a futex |
486 | * @uaddr: virtual address of the futex | 491 | * @uaddr: virtual address of the futex |
487 | * @fshared: 0 for a PROCESS_PRIVATE futex, 1 for PROCESS_SHARED | 492 | * @fshared: 0 for a PROCESS_PRIVATE futex, 1 for PROCESS_SHARED |
488 | * @key: address where result is stored. | 493 | * @key: address where result is stored. |
489 | * @rw: mapping needs to be read/write (values: VERIFY_READ, | 494 | * @rw: mapping needs to be read/write (values: FUTEX_READ, |
490 | * VERIFY_WRITE) | 495 | * FUTEX_WRITE) |
491 | * | 496 | * |
492 | * Return: a negative error code or 0 | 497 | * Return: a negative error code or 0 |
493 | * | 498 | * |
@@ -500,7 +505,7 @@ static void drop_futex_key_refs(union futex_key *key) | |||
500 | * lock_page() might sleep, the caller should not hold a spinlock. | 505 | * lock_page() might sleep, the caller should not hold a spinlock. |
501 | */ | 506 | */ |
502 | static int | 507 | static int |
503 | get_futex_key(u32 __user *uaddr, int fshared, union futex_key *key, int rw) | 508 | get_futex_key(u32 __user *uaddr, int fshared, union futex_key *key, enum futex_access rw) |
504 | { | 509 | { |
505 | unsigned long address = (unsigned long)uaddr; | 510 | unsigned long address = (unsigned long)uaddr; |
506 | struct mm_struct *mm = current->mm; | 511 | struct mm_struct *mm = current->mm; |
@@ -516,7 +521,7 @@ get_futex_key(u32 __user *uaddr, int fshared, union futex_key *key, int rw) | |||
516 | return -EINVAL; | 521 | return -EINVAL; |
517 | address -= key->both.offset; | 522 | address -= key->both.offset; |
518 | 523 | ||
519 | if (unlikely(!access_ok(rw, uaddr, sizeof(u32)))) | 524 | if (unlikely(!access_ok(uaddr, sizeof(u32)))) |
520 | return -EFAULT; | 525 | return -EFAULT; |
521 | 526 | ||
522 | if (unlikely(should_fail_futex(fshared))) | 527 | if (unlikely(should_fail_futex(fshared))) |
@@ -546,7 +551,7 @@ again: | |||
546 | * If write access is not required (eg. FUTEX_WAIT), try | 551 | * If write access is not required (eg. FUTEX_WAIT), try |
547 | * and get read-only access. | 552 | * and get read-only access. |
548 | */ | 553 | */ |
549 | if (err == -EFAULT && rw == VERIFY_READ) { | 554 | if (err == -EFAULT && rw == FUTEX_READ) { |
550 | err = get_user_pages_fast(address, 1, 0, &page); | 555 | err = get_user_pages_fast(address, 1, 0, &page); |
551 | ro = 1; | 556 | ro = 1; |
552 | } | 557 | } |
@@ -1583,7 +1588,7 @@ futex_wake(u32 __user *uaddr, unsigned int flags, int nr_wake, u32 bitset) | |||
1583 | if (!bitset) | 1588 | if (!bitset) |
1584 | return -EINVAL; | 1589 | return -EINVAL; |
1585 | 1590 | ||
1586 | ret = get_futex_key(uaddr, flags & FLAGS_SHARED, &key, VERIFY_READ); | 1591 | ret = get_futex_key(uaddr, flags & FLAGS_SHARED, &key, FUTEX_READ); |
1587 | if (unlikely(ret != 0)) | 1592 | if (unlikely(ret != 0)) |
1588 | goto out; | 1593 | goto out; |
1589 | 1594 | ||
@@ -1642,7 +1647,7 @@ static int futex_atomic_op_inuser(unsigned int encoded_op, u32 __user *uaddr) | |||
1642 | oparg = 1 << oparg; | 1647 | oparg = 1 << oparg; |
1643 | } | 1648 | } |
1644 | 1649 | ||
1645 | if (!access_ok(VERIFY_WRITE, uaddr, sizeof(u32))) | 1650 | if (!access_ok(uaddr, sizeof(u32))) |
1646 | return -EFAULT; | 1651 | return -EFAULT; |
1647 | 1652 | ||
1648 | ret = arch_futex_atomic_op_inuser(op, oparg, &oldval, uaddr); | 1653 | ret = arch_futex_atomic_op_inuser(op, oparg, &oldval, uaddr); |
@@ -1682,10 +1687,10 @@ futex_wake_op(u32 __user *uaddr1, unsigned int flags, u32 __user *uaddr2, | |||
1682 | DEFINE_WAKE_Q(wake_q); | 1687 | DEFINE_WAKE_Q(wake_q); |
1683 | 1688 | ||
1684 | retry: | 1689 | retry: |
1685 | ret = get_futex_key(uaddr1, flags & FLAGS_SHARED, &key1, VERIFY_READ); | 1690 | ret = get_futex_key(uaddr1, flags & FLAGS_SHARED, &key1, FUTEX_READ); |
1686 | if (unlikely(ret != 0)) | 1691 | if (unlikely(ret != 0)) |
1687 | goto out; | 1692 | goto out; |
1688 | ret = get_futex_key(uaddr2, flags & FLAGS_SHARED, &key2, VERIFY_WRITE); | 1693 | ret = get_futex_key(uaddr2, flags & FLAGS_SHARED, &key2, FUTEX_WRITE); |
1689 | if (unlikely(ret != 0)) | 1694 | if (unlikely(ret != 0)) |
1690 | goto out_put_key1; | 1695 | goto out_put_key1; |
1691 | 1696 | ||
@@ -1961,11 +1966,11 @@ static int futex_requeue(u32 __user *uaddr1, unsigned int flags, | |||
1961 | } | 1966 | } |
1962 | 1967 | ||
1963 | retry: | 1968 | retry: |
1964 | ret = get_futex_key(uaddr1, flags & FLAGS_SHARED, &key1, VERIFY_READ); | 1969 | ret = get_futex_key(uaddr1, flags & FLAGS_SHARED, &key1, FUTEX_READ); |
1965 | if (unlikely(ret != 0)) | 1970 | if (unlikely(ret != 0)) |
1966 | goto out; | 1971 | goto out; |
1967 | ret = get_futex_key(uaddr2, flags & FLAGS_SHARED, &key2, | 1972 | ret = get_futex_key(uaddr2, flags & FLAGS_SHARED, &key2, |
1968 | requeue_pi ? VERIFY_WRITE : VERIFY_READ); | 1973 | requeue_pi ? FUTEX_WRITE : FUTEX_READ); |
1969 | if (unlikely(ret != 0)) | 1974 | if (unlikely(ret != 0)) |
1970 | goto out_put_key1; | 1975 | goto out_put_key1; |
1971 | 1976 | ||
@@ -2634,7 +2639,7 @@ static int futex_wait_setup(u32 __user *uaddr, u32 val, unsigned int flags, | |||
2634 | * while the syscall executes. | 2639 | * while the syscall executes. |
2635 | */ | 2640 | */ |
2636 | retry: | 2641 | retry: |
2637 | ret = get_futex_key(uaddr, flags & FLAGS_SHARED, &q->key, VERIFY_READ); | 2642 | ret = get_futex_key(uaddr, flags & FLAGS_SHARED, &q->key, FUTEX_READ); |
2638 | if (unlikely(ret != 0)) | 2643 | if (unlikely(ret != 0)) |
2639 | return ret; | 2644 | return ret; |
2640 | 2645 | ||
@@ -2793,7 +2798,7 @@ static int futex_lock_pi(u32 __user *uaddr, unsigned int flags, | |||
2793 | } | 2798 | } |
2794 | 2799 | ||
2795 | retry: | 2800 | retry: |
2796 | ret = get_futex_key(uaddr, flags & FLAGS_SHARED, &q.key, VERIFY_WRITE); | 2801 | ret = get_futex_key(uaddr, flags & FLAGS_SHARED, &q.key, FUTEX_WRITE); |
2797 | if (unlikely(ret != 0)) | 2802 | if (unlikely(ret != 0)) |
2798 | goto out; | 2803 | goto out; |
2799 | 2804 | ||
@@ -2972,7 +2977,7 @@ retry: | |||
2972 | if ((uval & FUTEX_TID_MASK) != vpid) | 2977 | if ((uval & FUTEX_TID_MASK) != vpid) |
2973 | return -EPERM; | 2978 | return -EPERM; |
2974 | 2979 | ||
2975 | ret = get_futex_key(uaddr, flags & FLAGS_SHARED, &key, VERIFY_WRITE); | 2980 | ret = get_futex_key(uaddr, flags & FLAGS_SHARED, &key, FUTEX_WRITE); |
2976 | if (ret) | 2981 | if (ret) |
2977 | return ret; | 2982 | return ret; |
2978 | 2983 | ||
@@ -3199,7 +3204,7 @@ static int futex_wait_requeue_pi(u32 __user *uaddr, unsigned int flags, | |||
3199 | */ | 3204 | */ |
3200 | rt_mutex_init_waiter(&rt_waiter); | 3205 | rt_mutex_init_waiter(&rt_waiter); |
3201 | 3206 | ||
3202 | ret = get_futex_key(uaddr2, flags & FLAGS_SHARED, &key2, VERIFY_WRITE); | 3207 | ret = get_futex_key(uaddr2, flags & FLAGS_SHARED, &key2, FUTEX_WRITE); |
3203 | if (unlikely(ret != 0)) | 3208 | if (unlikely(ret != 0)) |
3204 | goto out; | 3209 | goto out; |
3205 | 3210 | ||
diff --git a/kernel/printk/printk.c b/kernel/printk/printk.c index 1306fe0c1dc6..d3d170374ceb 100644 --- a/kernel/printk/printk.c +++ b/kernel/printk/printk.c | |||
@@ -1466,7 +1466,7 @@ int do_syslog(int type, char __user *buf, int len, int source) | |||
1466 | return -EINVAL; | 1466 | return -EINVAL; |
1467 | if (!len) | 1467 | if (!len) |
1468 | return 0; | 1468 | return 0; |
1469 | if (!access_ok(VERIFY_WRITE, buf, len)) | 1469 | if (!access_ok(buf, len)) |
1470 | return -EFAULT; | 1470 | return -EFAULT; |
1471 | error = wait_event_interruptible(log_wait, | 1471 | error = wait_event_interruptible(log_wait, |
1472 | syslog_seq != log_next_seq); | 1472 | syslog_seq != log_next_seq); |
@@ -1484,7 +1484,7 @@ int do_syslog(int type, char __user *buf, int len, int source) | |||
1484 | return -EINVAL; | 1484 | return -EINVAL; |
1485 | if (!len) | 1485 | if (!len) |
1486 | return 0; | 1486 | return 0; |
1487 | if (!access_ok(VERIFY_WRITE, buf, len)) | 1487 | if (!access_ok(buf, len)) |
1488 | return -EFAULT; | 1488 | return -EFAULT; |
1489 | error = syslog_print_all(buf, len, clear); | 1489 | error = syslog_print_all(buf, len, clear); |
1490 | break; | 1490 | break; |
diff --git a/kernel/ptrace.c b/kernel/ptrace.c index c2cee9db5204..771e93f9c43f 100644 --- a/kernel/ptrace.c +++ b/kernel/ptrace.c | |||
@@ -1073,7 +1073,7 @@ int ptrace_request(struct task_struct *child, long request, | |||
1073 | struct iovec kiov; | 1073 | struct iovec kiov; |
1074 | struct iovec __user *uiov = datavp; | 1074 | struct iovec __user *uiov = datavp; |
1075 | 1075 | ||
1076 | if (!access_ok(VERIFY_WRITE, uiov, sizeof(*uiov))) | 1076 | if (!access_ok(uiov, sizeof(*uiov))) |
1077 | return -EFAULT; | 1077 | return -EFAULT; |
1078 | 1078 | ||
1079 | if (__get_user(kiov.iov_base, &uiov->iov_base) || | 1079 | if (__get_user(kiov.iov_base, &uiov->iov_base) || |
@@ -1229,7 +1229,7 @@ int compat_ptrace_request(struct task_struct *child, compat_long_t request, | |||
1229 | compat_uptr_t ptr; | 1229 | compat_uptr_t ptr; |
1230 | compat_size_t len; | 1230 | compat_size_t len; |
1231 | 1231 | ||
1232 | if (!access_ok(VERIFY_WRITE, uiov, sizeof(*uiov))) | 1232 | if (!access_ok(uiov, sizeof(*uiov))) |
1233 | return -EFAULT; | 1233 | return -EFAULT; |
1234 | 1234 | ||
1235 | if (__get_user(ptr, &uiov->iov_base) || | 1235 | if (__get_user(ptr, &uiov->iov_base) || |
diff --git a/kernel/rseq.c b/kernel/rseq.c index c6242d8594dc..25e9a7b60eba 100644 --- a/kernel/rseq.c +++ b/kernel/rseq.c | |||
@@ -267,7 +267,7 @@ void __rseq_handle_notify_resume(struct ksignal *ksig, struct pt_regs *regs) | |||
267 | 267 | ||
268 | if (unlikely(t->flags & PF_EXITING)) | 268 | if (unlikely(t->flags & PF_EXITING)) |
269 | return; | 269 | return; |
270 | if (unlikely(!access_ok(VERIFY_WRITE, t->rseq, sizeof(*t->rseq)))) | 270 | if (unlikely(!access_ok(t->rseq, sizeof(*t->rseq)))) |
271 | goto error; | 271 | goto error; |
272 | ret = rseq_ip_fixup(regs); | 272 | ret = rseq_ip_fixup(regs); |
273 | if (unlikely(ret < 0)) | 273 | if (unlikely(ret < 0)) |
@@ -295,7 +295,7 @@ void rseq_syscall(struct pt_regs *regs) | |||
295 | 295 | ||
296 | if (!t->rseq) | 296 | if (!t->rseq) |
297 | return; | 297 | return; |
298 | if (!access_ok(VERIFY_READ, t->rseq, sizeof(*t->rseq)) || | 298 | if (!access_ok(t->rseq, sizeof(*t->rseq)) || |
299 | rseq_get_rseq_cs(t, &rseq_cs) || in_rseq_cs(ip, &rseq_cs)) | 299 | rseq_get_rseq_cs(t, &rseq_cs) || in_rseq_cs(ip, &rseq_cs)) |
300 | force_sig(SIGSEGV, t); | 300 | force_sig(SIGSEGV, t); |
301 | } | 301 | } |
@@ -351,7 +351,7 @@ SYSCALL_DEFINE4(rseq, struct rseq __user *, rseq, u32, rseq_len, | |||
351 | if (!IS_ALIGNED((unsigned long)rseq, __alignof__(*rseq)) || | 351 | if (!IS_ALIGNED((unsigned long)rseq, __alignof__(*rseq)) || |
352 | rseq_len != sizeof(*rseq)) | 352 | rseq_len != sizeof(*rseq)) |
353 | return -EINVAL; | 353 | return -EINVAL; |
354 | if (!access_ok(VERIFY_WRITE, rseq, rseq_len)) | 354 | if (!access_ok(rseq, rseq_len)) |
355 | return -EFAULT; | 355 | return -EFAULT; |
356 | current->rseq = rseq; | 356 | current->rseq = rseq; |
357 | current->rseq_len = rseq_len; | 357 | current->rseq_len = rseq_len; |
diff --git a/kernel/sched/core.c b/kernel/sched/core.c index 17a954c9e153..223f78d5c111 100644 --- a/kernel/sched/core.c +++ b/kernel/sched/core.c | |||
@@ -4450,7 +4450,7 @@ static int sched_copy_attr(struct sched_attr __user *uattr, struct sched_attr *a | |||
4450 | u32 size; | 4450 | u32 size; |
4451 | int ret; | 4451 | int ret; |
4452 | 4452 | ||
4453 | if (!access_ok(VERIFY_WRITE, uattr, SCHED_ATTR_SIZE_VER0)) | 4453 | if (!access_ok(uattr, SCHED_ATTR_SIZE_VER0)) |
4454 | return -EFAULT; | 4454 | return -EFAULT; |
4455 | 4455 | ||
4456 | /* Zero the full structure, so that a short copy will be nice: */ | 4456 | /* Zero the full structure, so that a short copy will be nice: */ |
@@ -4650,7 +4650,7 @@ static int sched_read_attr(struct sched_attr __user *uattr, | |||
4650 | { | 4650 | { |
4651 | int ret; | 4651 | int ret; |
4652 | 4652 | ||
4653 | if (!access_ok(VERIFY_WRITE, uattr, usize)) | 4653 | if (!access_ok(uattr, usize)) |
4654 | return -EFAULT; | 4654 | return -EFAULT; |
4655 | 4655 | ||
4656 | /* | 4656 | /* |
diff --git a/kernel/signal.c b/kernel/signal.c index 53e07d97ffe0..e1d7ad8e6ab1 100644 --- a/kernel/signal.c +++ b/kernel/signal.c | |||
@@ -3997,7 +3997,7 @@ SYSCALL_DEFINE3(sigaction, int, sig, | |||
3997 | 3997 | ||
3998 | if (act) { | 3998 | if (act) { |
3999 | old_sigset_t mask; | 3999 | old_sigset_t mask; |
4000 | if (!access_ok(VERIFY_READ, act, sizeof(*act)) || | 4000 | if (!access_ok(act, sizeof(*act)) || |
4001 | __get_user(new_ka.sa.sa_handler, &act->sa_handler) || | 4001 | __get_user(new_ka.sa.sa_handler, &act->sa_handler) || |
4002 | __get_user(new_ka.sa.sa_restorer, &act->sa_restorer) || | 4002 | __get_user(new_ka.sa.sa_restorer, &act->sa_restorer) || |
4003 | __get_user(new_ka.sa.sa_flags, &act->sa_flags) || | 4003 | __get_user(new_ka.sa.sa_flags, &act->sa_flags) || |
@@ -4012,7 +4012,7 @@ SYSCALL_DEFINE3(sigaction, int, sig, | |||
4012 | ret = do_sigaction(sig, act ? &new_ka : NULL, oact ? &old_ka : NULL); | 4012 | ret = do_sigaction(sig, act ? &new_ka : NULL, oact ? &old_ka : NULL); |
4013 | 4013 | ||
4014 | if (!ret && oact) { | 4014 | if (!ret && oact) { |
4015 | if (!access_ok(VERIFY_WRITE, oact, sizeof(*oact)) || | 4015 | if (!access_ok(oact, sizeof(*oact)) || |
4016 | __put_user(old_ka.sa.sa_handler, &oact->sa_handler) || | 4016 | __put_user(old_ka.sa.sa_handler, &oact->sa_handler) || |
4017 | __put_user(old_ka.sa.sa_restorer, &oact->sa_restorer) || | 4017 | __put_user(old_ka.sa.sa_restorer, &oact->sa_restorer) || |
4018 | __put_user(old_ka.sa.sa_flags, &oact->sa_flags) || | 4018 | __put_user(old_ka.sa.sa_flags, &oact->sa_flags) || |
@@ -4034,7 +4034,7 @@ COMPAT_SYSCALL_DEFINE3(sigaction, int, sig, | |||
4034 | compat_uptr_t handler, restorer; | 4034 | compat_uptr_t handler, restorer; |
4035 | 4035 | ||
4036 | if (act) { | 4036 | if (act) { |
4037 | if (!access_ok(VERIFY_READ, act, sizeof(*act)) || | 4037 | if (!access_ok(act, sizeof(*act)) || |
4038 | __get_user(handler, &act->sa_handler) || | 4038 | __get_user(handler, &act->sa_handler) || |
4039 | __get_user(restorer, &act->sa_restorer) || | 4039 | __get_user(restorer, &act->sa_restorer) || |
4040 | __get_user(new_ka.sa.sa_flags, &act->sa_flags) || | 4040 | __get_user(new_ka.sa.sa_flags, &act->sa_flags) || |
@@ -4052,7 +4052,7 @@ COMPAT_SYSCALL_DEFINE3(sigaction, int, sig, | |||
4052 | ret = do_sigaction(sig, act ? &new_ka : NULL, oact ? &old_ka : NULL); | 4052 | ret = do_sigaction(sig, act ? &new_ka : NULL, oact ? &old_ka : NULL); |
4053 | 4053 | ||
4054 | if (!ret && oact) { | 4054 | if (!ret && oact) { |
4055 | if (!access_ok(VERIFY_WRITE, oact, sizeof(*oact)) || | 4055 | if (!access_ok(oact, sizeof(*oact)) || |
4056 | __put_user(ptr_to_compat(old_ka.sa.sa_handler), | 4056 | __put_user(ptr_to_compat(old_ka.sa.sa_handler), |
4057 | &oact->sa_handler) || | 4057 | &oact->sa_handler) || |
4058 | __put_user(ptr_to_compat(old_ka.sa.sa_restorer), | 4058 | __put_user(ptr_to_compat(old_ka.sa.sa_restorer), |
diff --git a/kernel/sys.c b/kernel/sys.c index 64b5a230f38d..a48cbf1414b8 100644 --- a/kernel/sys.c +++ b/kernel/sys.c | |||
@@ -2627,7 +2627,7 @@ COMPAT_SYSCALL_DEFINE1(sysinfo, struct compat_sysinfo __user *, info) | |||
2627 | s.freehigh >>= bitcount; | 2627 | s.freehigh >>= bitcount; |
2628 | } | 2628 | } |
2629 | 2629 | ||
2630 | if (!access_ok(VERIFY_WRITE, info, sizeof(struct compat_sysinfo)) || | 2630 | if (!access_ok(info, sizeof(struct compat_sysinfo)) || |
2631 | __put_user(s.uptime, &info->uptime) || | 2631 | __put_user(s.uptime, &info->uptime) || |
2632 | __put_user(s.loads[0], &info->loads[0]) || | 2632 | __put_user(s.loads[0], &info->loads[0]) || |
2633 | __put_user(s.loads[1], &info->loads[1]) || | 2633 | __put_user(s.loads[1], &info->loads[1]) || |
diff --git a/kernel/trace/bpf_trace.c b/kernel/trace/bpf_trace.c index 9ddb6fddb4e0..8b068adb9da1 100644 --- a/kernel/trace/bpf_trace.c +++ b/kernel/trace/bpf_trace.c | |||
@@ -170,7 +170,7 @@ BPF_CALL_3(bpf_probe_write_user, void *, unsafe_ptr, const void *, src, | |||
170 | return -EPERM; | 170 | return -EPERM; |
171 | if (unlikely(uaccess_kernel())) | 171 | if (unlikely(uaccess_kernel())) |
172 | return -EPERM; | 172 | return -EPERM; |
173 | if (!access_ok(VERIFY_WRITE, unsafe_ptr, size)) | 173 | if (!access_ok(unsafe_ptr, size)) |
174 | return -EPERM; | 174 | return -EPERM; |
175 | 175 | ||
176 | return probe_kernel_write(unsafe_ptr, src, size); | 176 | return probe_kernel_write(unsafe_ptr, src, size); |
diff --git a/lib/bitmap.c b/lib/bitmap.c index eead55aa7170..98872e9025da 100644 --- a/lib/bitmap.c +++ b/lib/bitmap.c | |||
@@ -443,7 +443,7 @@ int bitmap_parse_user(const char __user *ubuf, | |||
443 | unsigned int ulen, unsigned long *maskp, | 443 | unsigned int ulen, unsigned long *maskp, |
444 | int nmaskbits) | 444 | int nmaskbits) |
445 | { | 445 | { |
446 | if (!access_ok(VERIFY_READ, ubuf, ulen)) | 446 | if (!access_ok(ubuf, ulen)) |
447 | return -EFAULT; | 447 | return -EFAULT; |
448 | return __bitmap_parse((const char __force *)ubuf, | 448 | return __bitmap_parse((const char __force *)ubuf, |
449 | ulen, 1, maskp, nmaskbits); | 449 | ulen, 1, maskp, nmaskbits); |
@@ -641,7 +641,7 @@ int bitmap_parselist_user(const char __user *ubuf, | |||
641 | unsigned int ulen, unsigned long *maskp, | 641 | unsigned int ulen, unsigned long *maskp, |
642 | int nmaskbits) | 642 | int nmaskbits) |
643 | { | 643 | { |
644 | if (!access_ok(VERIFY_READ, ubuf, ulen)) | 644 | if (!access_ok(ubuf, ulen)) |
645 | return -EFAULT; | 645 | return -EFAULT; |
646 | return __bitmap_parselist((const char __force *)ubuf, | 646 | return __bitmap_parselist((const char __force *)ubuf, |
647 | ulen, 1, maskp, nmaskbits); | 647 | ulen, 1, maskp, nmaskbits); |
diff --git a/lib/iov_iter.c b/lib/iov_iter.c index 1928009f506e..c93870987b58 100644 --- a/lib/iov_iter.c +++ b/lib/iov_iter.c | |||
@@ -136,7 +136,7 @@ | |||
136 | 136 | ||
137 | static int copyout(void __user *to, const void *from, size_t n) | 137 | static int copyout(void __user *to, const void *from, size_t n) |
138 | { | 138 | { |
139 | if (access_ok(VERIFY_WRITE, to, n)) { | 139 | if (access_ok(to, n)) { |
140 | kasan_check_read(from, n); | 140 | kasan_check_read(from, n); |
141 | n = raw_copy_to_user(to, from, n); | 141 | n = raw_copy_to_user(to, from, n); |
142 | } | 142 | } |
@@ -145,7 +145,7 @@ static int copyout(void __user *to, const void *from, size_t n) | |||
145 | 145 | ||
146 | static int copyin(void *to, const void __user *from, size_t n) | 146 | static int copyin(void *to, const void __user *from, size_t n) |
147 | { | 147 | { |
148 | if (access_ok(VERIFY_READ, from, n)) { | 148 | if (access_ok(from, n)) { |
149 | kasan_check_write(to, n); | 149 | kasan_check_write(to, n); |
150 | n = raw_copy_from_user(to, from, n); | 150 | n = raw_copy_from_user(to, from, n); |
151 | } | 151 | } |
@@ -614,7 +614,7 @@ EXPORT_SYMBOL(_copy_to_iter); | |||
614 | #ifdef CONFIG_ARCH_HAS_UACCESS_MCSAFE | 614 | #ifdef CONFIG_ARCH_HAS_UACCESS_MCSAFE |
615 | static int copyout_mcsafe(void __user *to, const void *from, size_t n) | 615 | static int copyout_mcsafe(void __user *to, const void *from, size_t n) |
616 | { | 616 | { |
617 | if (access_ok(VERIFY_WRITE, to, n)) { | 617 | if (access_ok(to, n)) { |
618 | kasan_check_read(from, n); | 618 | kasan_check_read(from, n); |
619 | n = copy_to_user_mcsafe((__force void *) to, from, n); | 619 | n = copy_to_user_mcsafe((__force void *) to, from, n); |
620 | } | 620 | } |
@@ -1663,7 +1663,7 @@ int import_single_range(int rw, void __user *buf, size_t len, | |||
1663 | { | 1663 | { |
1664 | if (len > MAX_RW_COUNT) | 1664 | if (len > MAX_RW_COUNT) |
1665 | len = MAX_RW_COUNT; | 1665 | len = MAX_RW_COUNT; |
1666 | if (unlikely(!access_ok(!rw, buf, len))) | 1666 | if (unlikely(!access_ok(buf, len))) |
1667 | return -EFAULT; | 1667 | return -EFAULT; |
1668 | 1668 | ||
1669 | iov->iov_base = buf; | 1669 | iov->iov_base = buf; |
diff --git a/lib/strncpy_from_user.c b/lib/strncpy_from_user.c index b53e1b5d80f4..58eacd41526c 100644 --- a/lib/strncpy_from_user.c +++ b/lib/strncpy_from_user.c | |||
@@ -114,10 +114,11 @@ long strncpy_from_user(char *dst, const char __user *src, long count) | |||
114 | 114 | ||
115 | kasan_check_write(dst, count); | 115 | kasan_check_write(dst, count); |
116 | check_object_size(dst, count, false); | 116 | check_object_size(dst, count, false); |
117 | user_access_begin(); | 117 | if (user_access_begin(src, max)) { |
118 | retval = do_strncpy_from_user(dst, src, count, max); | 118 | retval = do_strncpy_from_user(dst, src, count, max); |
119 | user_access_end(); | 119 | user_access_end(); |
120 | return retval; | 120 | return retval; |
121 | } | ||
121 | } | 122 | } |
122 | return -EFAULT; | 123 | return -EFAULT; |
123 | } | 124 | } |
diff --git a/lib/strnlen_user.c b/lib/strnlen_user.c index 60d0bbda8f5e..1c1a1b0e38a5 100644 --- a/lib/strnlen_user.c +++ b/lib/strnlen_user.c | |||
@@ -114,10 +114,11 @@ long strnlen_user(const char __user *str, long count) | |||
114 | unsigned long max = max_addr - src_addr; | 114 | unsigned long max = max_addr - src_addr; |
115 | long retval; | 115 | long retval; |
116 | 116 | ||
117 | user_access_begin(); | 117 | if (user_access_begin(str, max)) { |
118 | retval = do_strnlen_user(str, count, max); | 118 | retval = do_strnlen_user(str, count, max); |
119 | user_access_end(); | 119 | user_access_end(); |
120 | return retval; | 120 | return retval; |
121 | } | ||
121 | } | 122 | } |
122 | return 0; | 123 | return 0; |
123 | } | 124 | } |
diff --git a/lib/usercopy.c b/lib/usercopy.c index 3744b2a8e591..c2bfbcaeb3dc 100644 --- a/lib/usercopy.c +++ b/lib/usercopy.c | |||
@@ -8,7 +8,7 @@ unsigned long _copy_from_user(void *to, const void __user *from, unsigned long n | |||
8 | { | 8 | { |
9 | unsigned long res = n; | 9 | unsigned long res = n; |
10 | might_fault(); | 10 | might_fault(); |
11 | if (likely(access_ok(VERIFY_READ, from, n))) { | 11 | if (likely(access_ok(from, n))) { |
12 | kasan_check_write(to, n); | 12 | kasan_check_write(to, n); |
13 | res = raw_copy_from_user(to, from, n); | 13 | res = raw_copy_from_user(to, from, n); |
14 | } | 14 | } |
@@ -23,7 +23,7 @@ EXPORT_SYMBOL(_copy_from_user); | |||
23 | unsigned long _copy_to_user(void __user *to, const void *from, unsigned long n) | 23 | unsigned long _copy_to_user(void __user *to, const void *from, unsigned long n) |
24 | { | 24 | { |
25 | might_fault(); | 25 | might_fault(); |
26 | if (likely(access_ok(VERIFY_WRITE, to, n))) { | 26 | if (likely(access_ok(to, n))) { |
27 | kasan_check_read(from, n); | 27 | kasan_check_read(from, n); |
28 | n = raw_copy_to_user(to, from, n); | 28 | n = raw_copy_to_user(to, from, n); |
29 | } | 29 | } |
@@ -1813,8 +1813,7 @@ int __get_user_pages_fast(unsigned long start, int nr_pages, int write, | |||
1813 | len = (unsigned long) nr_pages << PAGE_SHIFT; | 1813 | len = (unsigned long) nr_pages << PAGE_SHIFT; |
1814 | end = start + len; | 1814 | end = start + len; |
1815 | 1815 | ||
1816 | if (unlikely(!access_ok(write ? VERIFY_WRITE : VERIFY_READ, | 1816 | if (unlikely(!access_ok((void __user *)start, len))) |
1817 | (void __user *)start, len))) | ||
1818 | return 0; | 1817 | return 0; |
1819 | 1818 | ||
1820 | /* | 1819 | /* |
@@ -1868,8 +1867,7 @@ int get_user_pages_fast(unsigned long start, int nr_pages, int write, | |||
1868 | if (nr_pages <= 0) | 1867 | if (nr_pages <= 0) |
1869 | return 0; | 1868 | return 0; |
1870 | 1869 | ||
1871 | if (unlikely(!access_ok(write ? VERIFY_WRITE : VERIFY_READ, | 1870 | if (unlikely(!access_ok((void __user *)start, len))) |
1872 | (void __user *)start, len))) | ||
1873 | return -EFAULT; | 1871 | return -EFAULT; |
1874 | 1872 | ||
1875 | if (gup_fast_permitted(start, nr_pages, write)) { | 1873 | if (gup_fast_permitted(start, nr_pages, write)) { |
diff --git a/mm/mincore.c b/mm/mincore.c index 4985965aa20a..218099b5ed31 100644 --- a/mm/mincore.c +++ b/mm/mincore.c | |||
@@ -233,14 +233,14 @@ SYSCALL_DEFINE3(mincore, unsigned long, start, size_t, len, | |||
233 | return -EINVAL; | 233 | return -EINVAL; |
234 | 234 | ||
235 | /* ..and we need to be passed a valid user-space range */ | 235 | /* ..and we need to be passed a valid user-space range */ |
236 | if (!access_ok(VERIFY_READ, (void __user *) start, len)) | 236 | if (!access_ok((void __user *) start, len)) |
237 | return -ENOMEM; | 237 | return -ENOMEM; |
238 | 238 | ||
239 | /* This also avoids any overflows on PAGE_ALIGN */ | 239 | /* This also avoids any overflows on PAGE_ALIGN */ |
240 | pages = len >> PAGE_SHIFT; | 240 | pages = len >> PAGE_SHIFT; |
241 | pages += (offset_in_page(len)) != 0; | 241 | pages += (offset_in_page(len)) != 0; |
242 | 242 | ||
243 | if (!access_ok(VERIFY_WRITE, vec, pages)) | 243 | if (!access_ok(vec, pages)) |
244 | return -EFAULT; | 244 | return -EFAULT; |
245 | 245 | ||
246 | tmp = (void *) __get_free_page(GFP_USER); | 246 | tmp = (void *) __get_free_page(GFP_USER); |
diff --git a/net/ax25/af_ax25.c b/net/ax25/af_ax25.c index c603d33d5410..5d01edf8d819 100644 --- a/net/ax25/af_ax25.c +++ b/net/ax25/af_ax25.c | |||
@@ -653,15 +653,22 @@ static int ax25_setsockopt(struct socket *sock, int level, int optname, | |||
653 | break; | 653 | break; |
654 | } | 654 | } |
655 | 655 | ||
656 | dev = dev_get_by_name(&init_net, devname); | 656 | rtnl_lock(); |
657 | dev = __dev_get_by_name(&init_net, devname); | ||
657 | if (!dev) { | 658 | if (!dev) { |
659 | rtnl_unlock(); | ||
658 | res = -ENODEV; | 660 | res = -ENODEV; |
659 | break; | 661 | break; |
660 | } | 662 | } |
661 | 663 | ||
662 | ax25->ax25_dev = ax25_dev_ax25dev(dev); | 664 | ax25->ax25_dev = ax25_dev_ax25dev(dev); |
665 | if (!ax25->ax25_dev) { | ||
666 | rtnl_unlock(); | ||
667 | res = -ENODEV; | ||
668 | break; | ||
669 | } | ||
663 | ax25_fillin_cb(ax25, ax25->ax25_dev); | 670 | ax25_fillin_cb(ax25, ax25->ax25_dev); |
664 | dev_put(dev); | 671 | rtnl_unlock(); |
665 | break; | 672 | break; |
666 | 673 | ||
667 | default: | 674 | default: |
diff --git a/net/ax25/ax25_dev.c b/net/ax25/ax25_dev.c index 9a3a301e1e2f..d92195cd7834 100644 --- a/net/ax25/ax25_dev.c +++ b/net/ax25/ax25_dev.c | |||
@@ -116,6 +116,7 @@ void ax25_dev_device_down(struct net_device *dev) | |||
116 | if ((s = ax25_dev_list) == ax25_dev) { | 116 | if ((s = ax25_dev_list) == ax25_dev) { |
117 | ax25_dev_list = s->next; | 117 | ax25_dev_list = s->next; |
118 | spin_unlock_bh(&ax25_dev_lock); | 118 | spin_unlock_bh(&ax25_dev_lock); |
119 | dev->ax25_ptr = NULL; | ||
119 | dev_put(dev); | 120 | dev_put(dev); |
120 | kfree(ax25_dev); | 121 | kfree(ax25_dev); |
121 | return; | 122 | return; |
@@ -125,6 +126,7 @@ void ax25_dev_device_down(struct net_device *dev) | |||
125 | if (s->next == ax25_dev) { | 126 | if (s->next == ax25_dev) { |
126 | s->next = ax25_dev->next; | 127 | s->next = ax25_dev->next; |
127 | spin_unlock_bh(&ax25_dev_lock); | 128 | spin_unlock_bh(&ax25_dev_lock); |
129 | dev->ax25_ptr = NULL; | ||
128 | dev_put(dev); | 130 | dev_put(dev); |
129 | kfree(ax25_dev); | 131 | kfree(ax25_dev); |
130 | return; | 132 | return; |
diff --git a/net/batman-adv/icmp_socket.c b/net/batman-adv/icmp_socket.c index d70f363c52ae..6d5859714f52 100644 --- a/net/batman-adv/icmp_socket.c +++ b/net/batman-adv/icmp_socket.c | |||
@@ -147,7 +147,7 @@ static ssize_t batadv_socket_read(struct file *file, char __user *buf, | |||
147 | if (!buf || count < sizeof(struct batadv_icmp_packet)) | 147 | if (!buf || count < sizeof(struct batadv_icmp_packet)) |
148 | return -EINVAL; | 148 | return -EINVAL; |
149 | 149 | ||
150 | if (!access_ok(VERIFY_WRITE, buf, count)) | 150 | if (!access_ok(buf, count)) |
151 | return -EFAULT; | 151 | return -EFAULT; |
152 | 152 | ||
153 | error = wait_event_interruptible(socket_client->queue_wait, | 153 | error = wait_event_interruptible(socket_client->queue_wait, |
diff --git a/net/batman-adv/log.c b/net/batman-adv/log.c index 02e55b78132f..75f602e1ce94 100644 --- a/net/batman-adv/log.c +++ b/net/batman-adv/log.c | |||
@@ -136,7 +136,7 @@ static ssize_t batadv_log_read(struct file *file, char __user *buf, | |||
136 | if (count == 0) | 136 | if (count == 0) |
137 | return 0; | 137 | return 0; |
138 | 138 | ||
139 | if (!access_ok(VERIFY_WRITE, buf, count)) | 139 | if (!access_ok(buf, count)) |
140 | return -EFAULT; | 140 | return -EFAULT; |
141 | 141 | ||
142 | error = wait_event_interruptible(debug_log->queue_wait, | 142 | error = wait_event_interruptible(debug_log->queue_wait, |
diff --git a/net/compat.c b/net/compat.c index f7084780a8f8..959d1c51826d 100644 --- a/net/compat.c +++ b/net/compat.c | |||
@@ -358,7 +358,7 @@ static int do_set_sock_timeout(struct socket *sock, int level, | |||
358 | 358 | ||
359 | if (optlen < sizeof(*up)) | 359 | if (optlen < sizeof(*up)) |
360 | return -EINVAL; | 360 | return -EINVAL; |
361 | if (!access_ok(VERIFY_READ, up, sizeof(*up)) || | 361 | if (!access_ok(up, sizeof(*up)) || |
362 | __get_user(ktime.tv_sec, &up->tv_sec) || | 362 | __get_user(ktime.tv_sec, &up->tv_sec) || |
363 | __get_user(ktime.tv_usec, &up->tv_usec)) | 363 | __get_user(ktime.tv_usec, &up->tv_usec)) |
364 | return -EFAULT; | 364 | return -EFAULT; |
@@ -438,7 +438,7 @@ static int do_get_sock_timeout(struct socket *sock, int level, int optname, | |||
438 | 438 | ||
439 | if (!err) { | 439 | if (!err) { |
440 | if (put_user(sizeof(*up), optlen) || | 440 | if (put_user(sizeof(*up), optlen) || |
441 | !access_ok(VERIFY_WRITE, up, sizeof(*up)) || | 441 | !access_ok(up, sizeof(*up)) || |
442 | __put_user(ktime.tv_sec, &up->tv_sec) || | 442 | __put_user(ktime.tv_sec, &up->tv_sec) || |
443 | __put_user(ktime.tv_usec, &up->tv_usec)) | 443 | __put_user(ktime.tv_usec, &up->tv_usec)) |
444 | err = -EFAULT; | 444 | err = -EFAULT; |
@@ -467,12 +467,14 @@ int compat_sock_get_timestamp(struct sock *sk, struct timeval __user *userstamp) | |||
467 | ctv = (struct compat_timeval __user *) userstamp; | 467 | ctv = (struct compat_timeval __user *) userstamp; |
468 | err = -ENOENT; | 468 | err = -ENOENT; |
469 | sock_enable_timestamp(sk, SOCK_TIMESTAMP); | 469 | sock_enable_timestamp(sk, SOCK_TIMESTAMP); |
470 | tv = ktime_to_timeval(sk->sk_stamp); | 470 | tv = ktime_to_timeval(sock_read_timestamp(sk)); |
471 | |||
471 | if (tv.tv_sec == -1) | 472 | if (tv.tv_sec == -1) |
472 | return err; | 473 | return err; |
473 | if (tv.tv_sec == 0) { | 474 | if (tv.tv_sec == 0) { |
474 | sk->sk_stamp = ktime_get_real(); | 475 | ktime_t kt = ktime_get_real(); |
475 | tv = ktime_to_timeval(sk->sk_stamp); | 476 | sock_write_timestamp(sk, kt); |
477 | tv = ktime_to_timeval(kt); | ||
476 | } | 478 | } |
477 | err = 0; | 479 | err = 0; |
478 | if (put_user(tv.tv_sec, &ctv->tv_sec) || | 480 | if (put_user(tv.tv_sec, &ctv->tv_sec) || |
@@ -494,12 +496,13 @@ int compat_sock_get_timestampns(struct sock *sk, struct timespec __user *usersta | |||
494 | ctv = (struct compat_timespec __user *) userstamp; | 496 | ctv = (struct compat_timespec __user *) userstamp; |
495 | err = -ENOENT; | 497 | err = -ENOENT; |
496 | sock_enable_timestamp(sk, SOCK_TIMESTAMP); | 498 | sock_enable_timestamp(sk, SOCK_TIMESTAMP); |
497 | ts = ktime_to_timespec(sk->sk_stamp); | 499 | ts = ktime_to_timespec(sock_read_timestamp(sk)); |
498 | if (ts.tv_sec == -1) | 500 | if (ts.tv_sec == -1) |
499 | return err; | 501 | return err; |
500 | if (ts.tv_sec == 0) { | 502 | if (ts.tv_sec == 0) { |
501 | sk->sk_stamp = ktime_get_real(); | 503 | ktime_t kt = ktime_get_real(); |
502 | ts = ktime_to_timespec(sk->sk_stamp); | 504 | sock_write_timestamp(sk, kt); |
505 | ts = ktime_to_timespec(kt); | ||
503 | } | 506 | } |
504 | err = 0; | 507 | err = 0; |
505 | if (put_user(ts.tv_sec, &ctv->tv_sec) || | 508 | if (put_user(ts.tv_sec, &ctv->tv_sec) || |
@@ -587,8 +590,8 @@ int compat_mc_setsockopt(struct sock *sock, int level, int optname, | |||
587 | compat_alloc_user_space(sizeof(struct group_req)); | 590 | compat_alloc_user_space(sizeof(struct group_req)); |
588 | u32 interface; | 591 | u32 interface; |
589 | 592 | ||
590 | if (!access_ok(VERIFY_READ, gr32, sizeof(*gr32)) || | 593 | if (!access_ok(gr32, sizeof(*gr32)) || |
591 | !access_ok(VERIFY_WRITE, kgr, sizeof(struct group_req)) || | 594 | !access_ok(kgr, sizeof(struct group_req)) || |
592 | __get_user(interface, &gr32->gr_interface) || | 595 | __get_user(interface, &gr32->gr_interface) || |
593 | __put_user(interface, &kgr->gr_interface) || | 596 | __put_user(interface, &kgr->gr_interface) || |
594 | copy_in_user(&kgr->gr_group, &gr32->gr_group, | 597 | copy_in_user(&kgr->gr_group, &gr32->gr_group, |
@@ -608,8 +611,8 @@ int compat_mc_setsockopt(struct sock *sock, int level, int optname, | |||
608 | sizeof(struct group_source_req)); | 611 | sizeof(struct group_source_req)); |
609 | u32 interface; | 612 | u32 interface; |
610 | 613 | ||
611 | if (!access_ok(VERIFY_READ, gsr32, sizeof(*gsr32)) || | 614 | if (!access_ok(gsr32, sizeof(*gsr32)) || |
612 | !access_ok(VERIFY_WRITE, kgsr, | 615 | !access_ok(kgsr, |
613 | sizeof(struct group_source_req)) || | 616 | sizeof(struct group_source_req)) || |
614 | __get_user(interface, &gsr32->gsr_interface) || | 617 | __get_user(interface, &gsr32->gsr_interface) || |
615 | __put_user(interface, &kgsr->gsr_interface) || | 618 | __put_user(interface, &kgsr->gsr_interface) || |
@@ -628,7 +631,7 @@ int compat_mc_setsockopt(struct sock *sock, int level, int optname, | |||
628 | struct group_filter __user *kgf; | 631 | struct group_filter __user *kgf; |
629 | u32 interface, fmode, numsrc; | 632 | u32 interface, fmode, numsrc; |
630 | 633 | ||
631 | if (!access_ok(VERIFY_READ, gf32, __COMPAT_GF0_SIZE) || | 634 | if (!access_ok(gf32, __COMPAT_GF0_SIZE) || |
632 | __get_user(interface, &gf32->gf_interface) || | 635 | __get_user(interface, &gf32->gf_interface) || |
633 | __get_user(fmode, &gf32->gf_fmode) || | 636 | __get_user(fmode, &gf32->gf_fmode) || |
634 | __get_user(numsrc, &gf32->gf_numsrc)) | 637 | __get_user(numsrc, &gf32->gf_numsrc)) |
@@ -638,7 +641,7 @@ int compat_mc_setsockopt(struct sock *sock, int level, int optname, | |||
638 | if (koptlen < GROUP_FILTER_SIZE(numsrc)) | 641 | if (koptlen < GROUP_FILTER_SIZE(numsrc)) |
639 | return -EINVAL; | 642 | return -EINVAL; |
640 | kgf = compat_alloc_user_space(koptlen); | 643 | kgf = compat_alloc_user_space(koptlen); |
641 | if (!access_ok(VERIFY_WRITE, kgf, koptlen) || | 644 | if (!access_ok(kgf, koptlen) || |
642 | __put_user(interface, &kgf->gf_interface) || | 645 | __put_user(interface, &kgf->gf_interface) || |
643 | __put_user(fmode, &kgf->gf_fmode) || | 646 | __put_user(fmode, &kgf->gf_fmode) || |
644 | __put_user(numsrc, &kgf->gf_numsrc) || | 647 | __put_user(numsrc, &kgf->gf_numsrc) || |
@@ -672,7 +675,7 @@ int compat_mc_getsockopt(struct sock *sock, int level, int optname, | |||
672 | return getsockopt(sock, level, optname, optval, optlen); | 675 | return getsockopt(sock, level, optname, optval, optlen); |
673 | 676 | ||
674 | koptlen = compat_alloc_user_space(sizeof(*koptlen)); | 677 | koptlen = compat_alloc_user_space(sizeof(*koptlen)); |
675 | if (!access_ok(VERIFY_READ, optlen, sizeof(*optlen)) || | 678 | if (!access_ok(optlen, sizeof(*optlen)) || |
676 | __get_user(ulen, optlen)) | 679 | __get_user(ulen, optlen)) |
677 | return -EFAULT; | 680 | return -EFAULT; |
678 | 681 | ||
@@ -682,14 +685,14 @@ int compat_mc_getsockopt(struct sock *sock, int level, int optname, | |||
682 | if (klen < GROUP_FILTER_SIZE(0)) | 685 | if (klen < GROUP_FILTER_SIZE(0)) |
683 | return -EINVAL; | 686 | return -EINVAL; |
684 | 687 | ||
685 | if (!access_ok(VERIFY_WRITE, koptlen, sizeof(*koptlen)) || | 688 | if (!access_ok(koptlen, sizeof(*koptlen)) || |
686 | __put_user(klen, koptlen)) | 689 | __put_user(klen, koptlen)) |
687 | return -EFAULT; | 690 | return -EFAULT; |
688 | 691 | ||
689 | /* have to allow space for previous compat_alloc_user_space, too */ | 692 | /* have to allow space for previous compat_alloc_user_space, too */ |
690 | kgf = compat_alloc_user_space(klen+sizeof(*optlen)); | 693 | kgf = compat_alloc_user_space(klen+sizeof(*optlen)); |
691 | 694 | ||
692 | if (!access_ok(VERIFY_READ, gf32, __COMPAT_GF0_SIZE) || | 695 | if (!access_ok(gf32, __COMPAT_GF0_SIZE) || |
693 | __get_user(interface, &gf32->gf_interface) || | 696 | __get_user(interface, &gf32->gf_interface) || |
694 | __get_user(fmode, &gf32->gf_fmode) || | 697 | __get_user(fmode, &gf32->gf_fmode) || |
695 | __get_user(numsrc, &gf32->gf_numsrc) || | 698 | __get_user(numsrc, &gf32->gf_numsrc) || |
@@ -703,18 +706,18 @@ int compat_mc_getsockopt(struct sock *sock, int level, int optname, | |||
703 | if (err) | 706 | if (err) |
704 | return err; | 707 | return err; |
705 | 708 | ||
706 | if (!access_ok(VERIFY_READ, koptlen, sizeof(*koptlen)) || | 709 | if (!access_ok(koptlen, sizeof(*koptlen)) || |
707 | __get_user(klen, koptlen)) | 710 | __get_user(klen, koptlen)) |
708 | return -EFAULT; | 711 | return -EFAULT; |
709 | 712 | ||
710 | ulen = klen - (sizeof(*kgf)-sizeof(*gf32)); | 713 | ulen = klen - (sizeof(*kgf)-sizeof(*gf32)); |
711 | 714 | ||
712 | if (!access_ok(VERIFY_WRITE, optlen, sizeof(*optlen)) || | 715 | if (!access_ok(optlen, sizeof(*optlen)) || |
713 | __put_user(ulen, optlen)) | 716 | __put_user(ulen, optlen)) |
714 | return -EFAULT; | 717 | return -EFAULT; |
715 | 718 | ||
716 | if (!access_ok(VERIFY_READ, kgf, klen) || | 719 | if (!access_ok(kgf, klen) || |
717 | !access_ok(VERIFY_WRITE, gf32, ulen) || | 720 | !access_ok(gf32, ulen) || |
718 | __get_user(interface, &kgf->gf_interface) || | 721 | __get_user(interface, &kgf->gf_interface) || |
719 | __get_user(fmode, &kgf->gf_fmode) || | 722 | __get_user(fmode, &kgf->gf_fmode) || |
720 | __get_user(numsrc, &kgf->gf_numsrc) || | 723 | __get_user(numsrc, &kgf->gf_numsrc) || |
diff --git a/net/core/ethtool.c b/net/core/ethtool.c index d05402868575..158264f7cfaf 100644 --- a/net/core/ethtool.c +++ b/net/core/ethtool.c | |||
@@ -793,8 +793,13 @@ static noinline_for_stack int ethtool_get_drvinfo(struct net_device *dev, | |||
793 | if (rc >= 0) | 793 | if (rc >= 0) |
794 | info.n_priv_flags = rc; | 794 | info.n_priv_flags = rc; |
795 | } | 795 | } |
796 | if (ops->get_regs_len) | 796 | if (ops->get_regs_len) { |
797 | info.regdump_len = ops->get_regs_len(dev); | 797 | int ret = ops->get_regs_len(dev); |
798 | |||
799 | if (ret > 0) | ||
800 | info.regdump_len = ret; | ||
801 | } | ||
802 | |||
798 | if (ops->get_eeprom_len) | 803 | if (ops->get_eeprom_len) |
799 | info.eedump_len = ops->get_eeprom_len(dev); | 804 | info.eedump_len = ops->get_eeprom_len(dev); |
800 | 805 | ||
@@ -1337,6 +1342,9 @@ static int ethtool_get_regs(struct net_device *dev, char __user *useraddr) | |||
1337 | return -EFAULT; | 1342 | return -EFAULT; |
1338 | 1343 | ||
1339 | reglen = ops->get_regs_len(dev); | 1344 | reglen = ops->get_regs_len(dev); |
1345 | if (reglen <= 0) | ||
1346 | return reglen; | ||
1347 | |||
1340 | if (regs.len > reglen) | 1348 | if (regs.len > reglen) |
1341 | regs.len = reglen; | 1349 | regs.len = reglen; |
1342 | 1350 | ||
diff --git a/net/core/rtnetlink.c b/net/core/rtnetlink.c index 48f61885fd6f..5ea1bed08ede 100644 --- a/net/core/rtnetlink.c +++ b/net/core/rtnetlink.c | |||
@@ -4104,6 +4104,11 @@ static int rtnl_fdb_get(struct sk_buff *in_skb, struct nlmsghdr *nlh, | |||
4104 | if (err < 0) | 4104 | if (err < 0) |
4105 | return err; | 4105 | return err; |
4106 | 4106 | ||
4107 | if (!addr) { | ||
4108 | NL_SET_ERR_MSG(extack, "Missing lookup address for fdb get request"); | ||
4109 | return -EINVAL; | ||
4110 | } | ||
4111 | |||
4107 | if (brport_idx) { | 4112 | if (brport_idx) { |
4108 | dev = __dev_get_by_index(net, brport_idx); | 4113 | dev = __dev_get_by_index(net, brport_idx); |
4109 | if (!dev) { | 4114 | if (!dev) { |
diff --git a/net/core/sock.c b/net/core/sock.c index f00902c532cc..6aa2e7e0b4fb 100644 --- a/net/core/sock.c +++ b/net/core/sock.c | |||
@@ -2751,6 +2751,9 @@ void sock_init_data(struct socket *sock, struct sock *sk) | |||
2751 | sk->sk_sndtimeo = MAX_SCHEDULE_TIMEOUT; | 2751 | sk->sk_sndtimeo = MAX_SCHEDULE_TIMEOUT; |
2752 | 2752 | ||
2753 | sk->sk_stamp = SK_DEFAULT_STAMP; | 2753 | sk->sk_stamp = SK_DEFAULT_STAMP; |
2754 | #if BITS_PER_LONG==32 | ||
2755 | seqlock_init(&sk->sk_stamp_seq); | ||
2756 | #endif | ||
2754 | atomic_set(&sk->sk_zckey, 0); | 2757 | atomic_set(&sk->sk_zckey, 0); |
2755 | 2758 | ||
2756 | #ifdef CONFIG_NET_RX_BUSY_POLL | 2759 | #ifdef CONFIG_NET_RX_BUSY_POLL |
@@ -2850,12 +2853,13 @@ int sock_get_timestamp(struct sock *sk, struct timeval __user *userstamp) | |||
2850 | struct timeval tv; | 2853 | struct timeval tv; |
2851 | 2854 | ||
2852 | sock_enable_timestamp(sk, SOCK_TIMESTAMP); | 2855 | sock_enable_timestamp(sk, SOCK_TIMESTAMP); |
2853 | tv = ktime_to_timeval(sk->sk_stamp); | 2856 | tv = ktime_to_timeval(sock_read_timestamp(sk)); |
2854 | if (tv.tv_sec == -1) | 2857 | if (tv.tv_sec == -1) |
2855 | return -ENOENT; | 2858 | return -ENOENT; |
2856 | if (tv.tv_sec == 0) { | 2859 | if (tv.tv_sec == 0) { |
2857 | sk->sk_stamp = ktime_get_real(); | 2860 | ktime_t kt = ktime_get_real(); |
2858 | tv = ktime_to_timeval(sk->sk_stamp); | 2861 | sock_write_timestamp(sk, kt); |
2862 | tv = ktime_to_timeval(kt); | ||
2859 | } | 2863 | } |
2860 | return copy_to_user(userstamp, &tv, sizeof(tv)) ? -EFAULT : 0; | 2864 | return copy_to_user(userstamp, &tv, sizeof(tv)) ? -EFAULT : 0; |
2861 | } | 2865 | } |
@@ -2866,11 +2870,12 @@ int sock_get_timestampns(struct sock *sk, struct timespec __user *userstamp) | |||
2866 | struct timespec ts; | 2870 | struct timespec ts; |
2867 | 2871 | ||
2868 | sock_enable_timestamp(sk, SOCK_TIMESTAMP); | 2872 | sock_enable_timestamp(sk, SOCK_TIMESTAMP); |
2869 | ts = ktime_to_timespec(sk->sk_stamp); | 2873 | ts = ktime_to_timespec(sock_read_timestamp(sk)); |
2870 | if (ts.tv_sec == -1) | 2874 | if (ts.tv_sec == -1) |
2871 | return -ENOENT; | 2875 | return -ENOENT; |
2872 | if (ts.tv_sec == 0) { | 2876 | if (ts.tv_sec == 0) { |
2873 | sk->sk_stamp = ktime_get_real(); | 2877 | ktime_t kt = ktime_get_real(); |
2878 | sock_write_timestamp(sk, kt); | ||
2874 | ts = ktime_to_timespec(sk->sk_stamp); | 2879 | ts = ktime_to_timespec(sk->sk_stamp); |
2875 | } | 2880 | } |
2876 | return copy_to_user(userstamp, &ts, sizeof(ts)) ? -EFAULT : 0; | 2881 | return copy_to_user(userstamp, &ts, sizeof(ts)) ? -EFAULT : 0; |
diff --git a/net/ipv4/fib_rules.c b/net/ipv4/fib_rules.c index f8eb78d042a4..cfec3af54c8d 100644 --- a/net/ipv4/fib_rules.c +++ b/net/ipv4/fib_rules.c | |||
@@ -198,11 +198,15 @@ static int fib4_rule_match(struct fib_rule *rule, struct flowi *fl, int flags) | |||
198 | 198 | ||
199 | static struct fib_table *fib_empty_table(struct net *net) | 199 | static struct fib_table *fib_empty_table(struct net *net) |
200 | { | 200 | { |
201 | u32 id; | 201 | u32 id = 1; |
202 | 202 | ||
203 | for (id = 1; id <= RT_TABLE_MAX; id++) | 203 | while (1) { |
204 | if (!fib_get_table(net, id)) | 204 | if (!fib_get_table(net, id)) |
205 | return fib_new_table(net, id); | 205 | return fib_new_table(net, id); |
206 | |||
207 | if (id++ == RT_TABLE_MAX) | ||
208 | break; | ||
209 | } | ||
206 | return NULL; | 210 | return NULL; |
207 | } | 211 | } |
208 | 212 | ||
diff --git a/net/ipv4/ip_gre.c b/net/ipv4/ip_gre.c index c7a7bd58a23c..d1d09f3e5f9e 100644 --- a/net/ipv4/ip_gre.c +++ b/net/ipv4/ip_gre.c | |||
@@ -676,6 +676,9 @@ static netdev_tx_t ipgre_xmit(struct sk_buff *skb, | |||
676 | struct ip_tunnel *tunnel = netdev_priv(dev); | 676 | struct ip_tunnel *tunnel = netdev_priv(dev); |
677 | const struct iphdr *tnl_params; | 677 | const struct iphdr *tnl_params; |
678 | 678 | ||
679 | if (!pskb_inet_may_pull(skb)) | ||
680 | goto free_skb; | ||
681 | |||
679 | if (tunnel->collect_md) { | 682 | if (tunnel->collect_md) { |
680 | gre_fb_xmit(skb, dev, skb->protocol); | 683 | gre_fb_xmit(skb, dev, skb->protocol); |
681 | return NETDEV_TX_OK; | 684 | return NETDEV_TX_OK; |
@@ -719,6 +722,9 @@ static netdev_tx_t erspan_xmit(struct sk_buff *skb, | |||
719 | struct ip_tunnel *tunnel = netdev_priv(dev); | 722 | struct ip_tunnel *tunnel = netdev_priv(dev); |
720 | bool truncate = false; | 723 | bool truncate = false; |
721 | 724 | ||
725 | if (!pskb_inet_may_pull(skb)) | ||
726 | goto free_skb; | ||
727 | |||
722 | if (tunnel->collect_md) { | 728 | if (tunnel->collect_md) { |
723 | erspan_fb_xmit(skb, dev, skb->protocol); | 729 | erspan_fb_xmit(skb, dev, skb->protocol); |
724 | return NETDEV_TX_OK; | 730 | return NETDEV_TX_OK; |
@@ -762,6 +768,9 @@ static netdev_tx_t gre_tap_xmit(struct sk_buff *skb, | |||
762 | { | 768 | { |
763 | struct ip_tunnel *tunnel = netdev_priv(dev); | 769 | struct ip_tunnel *tunnel = netdev_priv(dev); |
764 | 770 | ||
771 | if (!pskb_inet_may_pull(skb)) | ||
772 | goto free_skb; | ||
773 | |||
765 | if (tunnel->collect_md) { | 774 | if (tunnel->collect_md) { |
766 | gre_fb_xmit(skb, dev, htons(ETH_P_TEB)); | 775 | gre_fb_xmit(skb, dev, htons(ETH_P_TEB)); |
767 | return NETDEV_TX_OK; | 776 | return NETDEV_TX_OK; |
diff --git a/net/ipv4/ip_tunnel.c b/net/ipv4/ip_tunnel.c index 284a22154b4e..c4f5602308ed 100644 --- a/net/ipv4/ip_tunnel.c +++ b/net/ipv4/ip_tunnel.c | |||
@@ -627,7 +627,6 @@ void ip_tunnel_xmit(struct sk_buff *skb, struct net_device *dev, | |||
627 | const struct iphdr *tnl_params, u8 protocol) | 627 | const struct iphdr *tnl_params, u8 protocol) |
628 | { | 628 | { |
629 | struct ip_tunnel *tunnel = netdev_priv(dev); | 629 | struct ip_tunnel *tunnel = netdev_priv(dev); |
630 | unsigned int inner_nhdr_len = 0; | ||
631 | const struct iphdr *inner_iph; | 630 | const struct iphdr *inner_iph; |
632 | struct flowi4 fl4; | 631 | struct flowi4 fl4; |
633 | u8 tos, ttl; | 632 | u8 tos, ttl; |
@@ -637,14 +636,6 @@ void ip_tunnel_xmit(struct sk_buff *skb, struct net_device *dev, | |||
637 | __be32 dst; | 636 | __be32 dst; |
638 | bool connected; | 637 | bool connected; |
639 | 638 | ||
640 | /* ensure we can access the inner net header, for several users below */ | ||
641 | if (skb->protocol == htons(ETH_P_IP)) | ||
642 | inner_nhdr_len = sizeof(struct iphdr); | ||
643 | else if (skb->protocol == htons(ETH_P_IPV6)) | ||
644 | inner_nhdr_len = sizeof(struct ipv6hdr); | ||
645 | if (unlikely(!pskb_may_pull(skb, inner_nhdr_len))) | ||
646 | goto tx_error; | ||
647 | |||
648 | inner_iph = (const struct iphdr *)skb_inner_network_header(skb); | 639 | inner_iph = (const struct iphdr *)skb_inner_network_header(skb); |
649 | connected = (tunnel->parms.iph.daddr != 0); | 640 | connected = (tunnel->parms.iph.daddr != 0); |
650 | 641 | ||
diff --git a/net/ipv4/ip_vti.c b/net/ipv4/ip_vti.c index de31b302d69c..d7b43e700023 100644 --- a/net/ipv4/ip_vti.c +++ b/net/ipv4/ip_vti.c | |||
@@ -241,6 +241,9 @@ static netdev_tx_t vti_tunnel_xmit(struct sk_buff *skb, struct net_device *dev) | |||
241 | struct ip_tunnel *tunnel = netdev_priv(dev); | 241 | struct ip_tunnel *tunnel = netdev_priv(dev); |
242 | struct flowi fl; | 242 | struct flowi fl; |
243 | 243 | ||
244 | if (!pskb_inet_may_pull(skb)) | ||
245 | goto tx_err; | ||
246 | |||
244 | memset(&fl, 0, sizeof(fl)); | 247 | memset(&fl, 0, sizeof(fl)); |
245 | 248 | ||
246 | switch (skb->protocol) { | 249 | switch (skb->protocol) { |
@@ -253,15 +256,18 @@ static netdev_tx_t vti_tunnel_xmit(struct sk_buff *skb, struct net_device *dev) | |||
253 | memset(IP6CB(skb), 0, sizeof(*IP6CB(skb))); | 256 | memset(IP6CB(skb), 0, sizeof(*IP6CB(skb))); |
254 | break; | 257 | break; |
255 | default: | 258 | default: |
256 | dev->stats.tx_errors++; | 259 | goto tx_err; |
257 | dev_kfree_skb(skb); | ||
258 | return NETDEV_TX_OK; | ||
259 | } | 260 | } |
260 | 261 | ||
261 | /* override mark with tunnel output key */ | 262 | /* override mark with tunnel output key */ |
262 | fl.flowi_mark = be32_to_cpu(tunnel->parms.o_key); | 263 | fl.flowi_mark = be32_to_cpu(tunnel->parms.o_key); |
263 | 264 | ||
264 | return vti_xmit(skb, dev, &fl); | 265 | return vti_xmit(skb, dev, &fl); |
266 | |||
267 | tx_err: | ||
268 | dev->stats.tx_errors++; | ||
269 | kfree_skb(skb); | ||
270 | return NETDEV_TX_OK; | ||
265 | } | 271 | } |
266 | 272 | ||
267 | static int vti4_err(struct sk_buff *skb, u32 info) | 273 | static int vti4_err(struct sk_buff *skb, u32 info) |
diff --git a/net/ipv6/addrconf.c b/net/ipv6/addrconf.c index 521e471f1cf9..8eeec6eb2bd3 100644 --- a/net/ipv6/addrconf.c +++ b/net/ipv6/addrconf.c | |||
@@ -4736,8 +4736,8 @@ inet6_rtm_newaddr(struct sk_buff *skb, struct nlmsghdr *nlh, | |||
4736 | IFA_F_MCAUTOJOIN | IFA_F_OPTIMISTIC; | 4736 | IFA_F_MCAUTOJOIN | IFA_F_OPTIMISTIC; |
4737 | 4737 | ||
4738 | idev = ipv6_find_idev(dev); | 4738 | idev = ipv6_find_idev(dev); |
4739 | if (IS_ERR(idev)) | 4739 | if (!idev) |
4740 | return PTR_ERR(idev); | 4740 | return -ENOBUFS; |
4741 | 4741 | ||
4742 | if (!ipv6_allow_optimistic_dad(net, idev)) | 4742 | if (!ipv6_allow_optimistic_dad(net, idev)) |
4743 | cfg.ifa_flags &= ~IFA_F_OPTIMISTIC; | 4743 | cfg.ifa_flags &= ~IFA_F_OPTIMISTIC; |
diff --git a/net/ipv6/af_inet6.c b/net/ipv6/af_inet6.c index f0cd291034f0..0bfb6cc0a30a 100644 --- a/net/ipv6/af_inet6.c +++ b/net/ipv6/af_inet6.c | |||
@@ -350,6 +350,9 @@ static int __inet6_bind(struct sock *sk, struct sockaddr *uaddr, int addr_len, | |||
350 | err = -EINVAL; | 350 | err = -EINVAL; |
351 | goto out_unlock; | 351 | goto out_unlock; |
352 | } | 352 | } |
353 | } | ||
354 | |||
355 | if (sk->sk_bound_dev_if) { | ||
353 | dev = dev_get_by_index_rcu(net, sk->sk_bound_dev_if); | 356 | dev = dev_get_by_index_rcu(net, sk->sk_bound_dev_if); |
354 | if (!dev) { | 357 | if (!dev) { |
355 | err = -ENODEV; | 358 | err = -ENODEV; |
diff --git a/net/ipv6/ip6_fib.c b/net/ipv6/ip6_fib.c index ae3786132c23..6613d8dbb0e5 100644 --- a/net/ipv6/ip6_fib.c +++ b/net/ipv6/ip6_fib.c | |||
@@ -627,7 +627,11 @@ static int inet6_dump_fib(struct sk_buff *skb, struct netlink_callback *cb) | |||
627 | return -ENOENT; | 627 | return -ENOENT; |
628 | } | 628 | } |
629 | 629 | ||
630 | res = fib6_dump_table(tb, skb, cb); | 630 | if (!cb->args[0]) { |
631 | res = fib6_dump_table(tb, skb, cb); | ||
632 | if (!res) | ||
633 | cb->args[0] = 1; | ||
634 | } | ||
631 | goto out; | 635 | goto out; |
632 | } | 636 | } |
633 | 637 | ||
diff --git a/net/ipv6/ip6_gre.c b/net/ipv6/ip6_gre.c index 229e55c99021..09d0826742f8 100644 --- a/net/ipv6/ip6_gre.c +++ b/net/ipv6/ip6_gre.c | |||
@@ -881,6 +881,9 @@ static netdev_tx_t ip6gre_tunnel_xmit(struct sk_buff *skb, | |||
881 | struct net_device_stats *stats = &t->dev->stats; | 881 | struct net_device_stats *stats = &t->dev->stats; |
882 | int ret; | 882 | int ret; |
883 | 883 | ||
884 | if (!pskb_inet_may_pull(skb)) | ||
885 | goto tx_err; | ||
886 | |||
884 | if (!ip6_tnl_xmit_ctl(t, &t->parms.laddr, &t->parms.raddr)) | 887 | if (!ip6_tnl_xmit_ctl(t, &t->parms.laddr, &t->parms.raddr)) |
885 | goto tx_err; | 888 | goto tx_err; |
886 | 889 | ||
@@ -923,6 +926,9 @@ static netdev_tx_t ip6erspan_tunnel_xmit(struct sk_buff *skb, | |||
923 | int nhoff; | 926 | int nhoff; |
924 | int thoff; | 927 | int thoff; |
925 | 928 | ||
929 | if (!pskb_inet_may_pull(skb)) | ||
930 | goto tx_err; | ||
931 | |||
926 | if (!ip6_tnl_xmit_ctl(t, &t->parms.laddr, &t->parms.raddr)) | 932 | if (!ip6_tnl_xmit_ctl(t, &t->parms.laddr, &t->parms.raddr)) |
927 | goto tx_err; | 933 | goto tx_err; |
928 | 934 | ||
@@ -995,8 +1001,6 @@ static netdev_tx_t ip6erspan_tunnel_xmit(struct sk_buff *skb, | |||
995 | goto tx_err; | 1001 | goto tx_err; |
996 | } | 1002 | } |
997 | } else { | 1003 | } else { |
998 | struct ipv6hdr *ipv6h = ipv6_hdr(skb); | ||
999 | |||
1000 | switch (skb->protocol) { | 1004 | switch (skb->protocol) { |
1001 | case htons(ETH_P_IP): | 1005 | case htons(ETH_P_IP): |
1002 | memset(&(IPCB(skb)->opt), 0, sizeof(IPCB(skb)->opt)); | 1006 | memset(&(IPCB(skb)->opt), 0, sizeof(IPCB(skb)->opt)); |
@@ -1004,7 +1008,7 @@ static netdev_tx_t ip6erspan_tunnel_xmit(struct sk_buff *skb, | |||
1004 | &dsfield, &encap_limit); | 1008 | &dsfield, &encap_limit); |
1005 | break; | 1009 | break; |
1006 | case htons(ETH_P_IPV6): | 1010 | case htons(ETH_P_IPV6): |
1007 | if (ipv6_addr_equal(&t->parms.raddr, &ipv6h->saddr)) | 1011 | if (ipv6_addr_equal(&t->parms.raddr, &ipv6_hdr(skb)->saddr)) |
1008 | goto tx_err; | 1012 | goto tx_err; |
1009 | if (prepare_ip6gre_xmit_ipv6(skb, dev, &fl6, | 1013 | if (prepare_ip6gre_xmit_ipv6(skb, dev, &fl6, |
1010 | &dsfield, &encap_limit)) | 1014 | &dsfield, &encap_limit)) |
diff --git a/net/ipv6/ip6_tunnel.c b/net/ipv6/ip6_tunnel.c index 99179b9c8384..0c6403cf8b52 100644 --- a/net/ipv6/ip6_tunnel.c +++ b/net/ipv6/ip6_tunnel.c | |||
@@ -1243,10 +1243,6 @@ ip4ip6_tnl_xmit(struct sk_buff *skb, struct net_device *dev) | |||
1243 | u8 tproto; | 1243 | u8 tproto; |
1244 | int err; | 1244 | int err; |
1245 | 1245 | ||
1246 | /* ensure we can access the full inner ip header */ | ||
1247 | if (!pskb_may_pull(skb, sizeof(struct iphdr))) | ||
1248 | return -1; | ||
1249 | |||
1250 | iph = ip_hdr(skb); | 1246 | iph = ip_hdr(skb); |
1251 | memset(&(IPCB(skb)->opt), 0, sizeof(IPCB(skb)->opt)); | 1247 | memset(&(IPCB(skb)->opt), 0, sizeof(IPCB(skb)->opt)); |
1252 | 1248 | ||
@@ -1321,9 +1317,6 @@ ip6ip6_tnl_xmit(struct sk_buff *skb, struct net_device *dev) | |||
1321 | u8 tproto; | 1317 | u8 tproto; |
1322 | int err; | 1318 | int err; |
1323 | 1319 | ||
1324 | if (unlikely(!pskb_may_pull(skb, sizeof(*ipv6h)))) | ||
1325 | return -1; | ||
1326 | |||
1327 | ipv6h = ipv6_hdr(skb); | 1320 | ipv6h = ipv6_hdr(skb); |
1328 | tproto = READ_ONCE(t->parms.proto); | 1321 | tproto = READ_ONCE(t->parms.proto); |
1329 | if ((tproto != IPPROTO_IPV6 && tproto != 0) || | 1322 | if ((tproto != IPPROTO_IPV6 && tproto != 0) || |
@@ -1405,6 +1398,9 @@ ip6_tnl_start_xmit(struct sk_buff *skb, struct net_device *dev) | |||
1405 | struct net_device_stats *stats = &t->dev->stats; | 1398 | struct net_device_stats *stats = &t->dev->stats; |
1406 | int ret; | 1399 | int ret; |
1407 | 1400 | ||
1401 | if (!pskb_inet_may_pull(skb)) | ||
1402 | goto tx_err; | ||
1403 | |||
1408 | switch (skb->protocol) { | 1404 | switch (skb->protocol) { |
1409 | case htons(ETH_P_IP): | 1405 | case htons(ETH_P_IP): |
1410 | ret = ip4ip6_tnl_xmit(skb, dev); | 1406 | ret = ip4ip6_tnl_xmit(skb, dev); |
diff --git a/net/ipv6/ip6_vti.c b/net/ipv6/ip6_vti.c index 706fe42e4928..8b6eefff2f7e 100644 --- a/net/ipv6/ip6_vti.c +++ b/net/ipv6/ip6_vti.c | |||
@@ -522,18 +522,18 @@ vti6_tnl_xmit(struct sk_buff *skb, struct net_device *dev) | |||
522 | { | 522 | { |
523 | struct ip6_tnl *t = netdev_priv(dev); | 523 | struct ip6_tnl *t = netdev_priv(dev); |
524 | struct net_device_stats *stats = &t->dev->stats; | 524 | struct net_device_stats *stats = &t->dev->stats; |
525 | struct ipv6hdr *ipv6h; | ||
526 | struct flowi fl; | 525 | struct flowi fl; |
527 | int ret; | 526 | int ret; |
528 | 527 | ||
528 | if (!pskb_inet_may_pull(skb)) | ||
529 | goto tx_err; | ||
530 | |||
529 | memset(&fl, 0, sizeof(fl)); | 531 | memset(&fl, 0, sizeof(fl)); |
530 | 532 | ||
531 | switch (skb->protocol) { | 533 | switch (skb->protocol) { |
532 | case htons(ETH_P_IPV6): | 534 | case htons(ETH_P_IPV6): |
533 | ipv6h = ipv6_hdr(skb); | ||
534 | |||
535 | if ((t->parms.proto != IPPROTO_IPV6 && t->parms.proto != 0) || | 535 | if ((t->parms.proto != IPPROTO_IPV6 && t->parms.proto != 0) || |
536 | vti6_addr_conflict(t, ipv6h)) | 536 | vti6_addr_conflict(t, ipv6_hdr(skb))) |
537 | goto tx_err; | 537 | goto tx_err; |
538 | 538 | ||
539 | xfrm_decode_session(skb, &fl, AF_INET6); | 539 | xfrm_decode_session(skb, &fl, AF_INET6); |
diff --git a/net/ipv6/ip6mr.c b/net/ipv6/ip6mr.c index 8276f1224f16..30337b38274b 100644 --- a/net/ipv6/ip6mr.c +++ b/net/ipv6/ip6mr.c | |||
@@ -51,6 +51,7 @@ | |||
51 | #include <linux/export.h> | 51 | #include <linux/export.h> |
52 | #include <net/ip6_checksum.h> | 52 | #include <net/ip6_checksum.h> |
53 | #include <linux/netconf.h> | 53 | #include <linux/netconf.h> |
54 | #include <net/ip_tunnels.h> | ||
54 | 55 | ||
55 | #include <linux/nospec.h> | 56 | #include <linux/nospec.h> |
56 | 57 | ||
@@ -599,13 +600,12 @@ static netdev_tx_t reg_vif_xmit(struct sk_buff *skb, | |||
599 | .flowi6_iif = skb->skb_iif ? : LOOPBACK_IFINDEX, | 600 | .flowi6_iif = skb->skb_iif ? : LOOPBACK_IFINDEX, |
600 | .flowi6_mark = skb->mark, | 601 | .flowi6_mark = skb->mark, |
601 | }; | 602 | }; |
602 | int err; | ||
603 | 603 | ||
604 | err = ip6mr_fib_lookup(net, &fl6, &mrt); | 604 | if (!pskb_inet_may_pull(skb)) |
605 | if (err < 0) { | 605 | goto tx_err; |
606 | kfree_skb(skb); | 606 | |
607 | return err; | 607 | if (ip6mr_fib_lookup(net, &fl6, &mrt) < 0) |
608 | } | 608 | goto tx_err; |
609 | 609 | ||
610 | read_lock(&mrt_lock); | 610 | read_lock(&mrt_lock); |
611 | dev->stats.tx_bytes += skb->len; | 611 | dev->stats.tx_bytes += skb->len; |
@@ -614,6 +614,11 @@ static netdev_tx_t reg_vif_xmit(struct sk_buff *skb, | |||
614 | read_unlock(&mrt_lock); | 614 | read_unlock(&mrt_lock); |
615 | kfree_skb(skb); | 615 | kfree_skb(skb); |
616 | return NETDEV_TX_OK; | 616 | return NETDEV_TX_OK; |
617 | |||
618 | tx_err: | ||
619 | dev->stats.tx_errors++; | ||
620 | kfree_skb(skb); | ||
621 | return NETDEV_TX_OK; | ||
617 | } | 622 | } |
618 | 623 | ||
619 | static int reg_vif_get_iflink(const struct net_device *dev) | 624 | static int reg_vif_get_iflink(const struct net_device *dev) |
diff --git a/net/ipv6/reassembly.c b/net/ipv6/reassembly.c index a5bb59ee50ac..36a3d8dc61f5 100644 --- a/net/ipv6/reassembly.c +++ b/net/ipv6/reassembly.c | |||
@@ -210,7 +210,7 @@ found: | |||
210 | if (next && next->ip_defrag_offset < end) | 210 | if (next && next->ip_defrag_offset < end) |
211 | goto discard_fq; | 211 | goto discard_fq; |
212 | 212 | ||
213 | /* Note : skb->ip_defrag_offset and skb->dev share the same location */ | 213 | /* Note : skb->ip_defrag_offset and skb->sk share the same location */ |
214 | dev = skb->dev; | 214 | dev = skb->dev; |
215 | if (dev) | 215 | if (dev) |
216 | fq->iif = dev->ifindex; | 216 | fq->iif = dev->ifindex; |
diff --git a/net/ipv6/route.c b/net/ipv6/route.c index 194bc162866d..40b225f87d5e 100644 --- a/net/ipv6/route.c +++ b/net/ipv6/route.c | |||
@@ -210,7 +210,9 @@ struct neighbour *ip6_neigh_lookup(const struct in6_addr *gw, | |||
210 | n = __ipv6_neigh_lookup(dev, daddr); | 210 | n = __ipv6_neigh_lookup(dev, daddr); |
211 | if (n) | 211 | if (n) |
212 | return n; | 212 | return n; |
213 | return neigh_create(&nd_tbl, daddr, dev); | 213 | |
214 | n = neigh_create(&nd_tbl, daddr, dev); | ||
215 | return IS_ERR(n) ? NULL : n; | ||
214 | } | 216 | } |
215 | 217 | ||
216 | static struct neighbour *ip6_dst_neigh_lookup(const struct dst_entry *dst, | 218 | static struct neighbour *ip6_dst_neigh_lookup(const struct dst_entry *dst, |
@@ -5054,12 +5056,16 @@ int ipv6_sysctl_rtcache_flush(struct ctl_table *ctl, int write, | |||
5054 | { | 5056 | { |
5055 | struct net *net; | 5057 | struct net *net; |
5056 | int delay; | 5058 | int delay; |
5059 | int ret; | ||
5057 | if (!write) | 5060 | if (!write) |
5058 | return -EINVAL; | 5061 | return -EINVAL; |
5059 | 5062 | ||
5060 | net = (struct net *)ctl->extra1; | 5063 | net = (struct net *)ctl->extra1; |
5061 | delay = net->ipv6.sysctl.flush_delay; | 5064 | delay = net->ipv6.sysctl.flush_delay; |
5062 | proc_dointvec(ctl, write, buffer, lenp, ppos); | 5065 | ret = proc_dointvec(ctl, write, buffer, lenp, ppos); |
5066 | if (ret) | ||
5067 | return ret; | ||
5068 | |||
5063 | fib6_run_gc(delay <= 0 ? 0 : (unsigned long)delay, net, delay > 0); | 5069 | fib6_run_gc(delay <= 0 ? 0 : (unsigned long)delay, net, delay > 0); |
5064 | return 0; | 5070 | return 0; |
5065 | } | 5071 | } |
diff --git a/net/ipv6/sit.c b/net/ipv6/sit.c index 51c9f75f34b9..1e03305c0549 100644 --- a/net/ipv6/sit.c +++ b/net/ipv6/sit.c | |||
@@ -1021,6 +1021,9 @@ tx_error: | |||
1021 | static netdev_tx_t sit_tunnel_xmit(struct sk_buff *skb, | 1021 | static netdev_tx_t sit_tunnel_xmit(struct sk_buff *skb, |
1022 | struct net_device *dev) | 1022 | struct net_device *dev) |
1023 | { | 1023 | { |
1024 | if (!pskb_inet_may_pull(skb)) | ||
1025 | goto tx_err; | ||
1026 | |||
1024 | switch (skb->protocol) { | 1027 | switch (skb->protocol) { |
1025 | case htons(ETH_P_IP): | 1028 | case htons(ETH_P_IP): |
1026 | sit_tunnel_xmit__(skb, dev, IPPROTO_IPIP); | 1029 | sit_tunnel_xmit__(skb, dev, IPPROTO_IPIP); |
diff --git a/net/netfilter/nf_conncount.c b/net/netfilter/nf_conncount.c index 9cd180bda092..7554c56b2e63 100644 --- a/net/netfilter/nf_conncount.c +++ b/net/netfilter/nf_conncount.c | |||
@@ -33,12 +33,6 @@ | |||
33 | 33 | ||
34 | #define CONNCOUNT_SLOTS 256U | 34 | #define CONNCOUNT_SLOTS 256U |
35 | 35 | ||
36 | #ifdef CONFIG_LOCKDEP | ||
37 | #define CONNCOUNT_LOCK_SLOTS 8U | ||
38 | #else | ||
39 | #define CONNCOUNT_LOCK_SLOTS 256U | ||
40 | #endif | ||
41 | |||
42 | #define CONNCOUNT_GC_MAX_NODES 8 | 36 | #define CONNCOUNT_GC_MAX_NODES 8 |
43 | #define MAX_KEYLEN 5 | 37 | #define MAX_KEYLEN 5 |
44 | 38 | ||
@@ -49,8 +43,6 @@ struct nf_conncount_tuple { | |||
49 | struct nf_conntrack_zone zone; | 43 | struct nf_conntrack_zone zone; |
50 | int cpu; | 44 | int cpu; |
51 | u32 jiffies32; | 45 | u32 jiffies32; |
52 | bool dead; | ||
53 | struct rcu_head rcu_head; | ||
54 | }; | 46 | }; |
55 | 47 | ||
56 | struct nf_conncount_rb { | 48 | struct nf_conncount_rb { |
@@ -60,7 +52,7 @@ struct nf_conncount_rb { | |||
60 | struct rcu_head rcu_head; | 52 | struct rcu_head rcu_head; |
61 | }; | 53 | }; |
62 | 54 | ||
63 | static spinlock_t nf_conncount_locks[CONNCOUNT_LOCK_SLOTS] __cacheline_aligned_in_smp; | 55 | static spinlock_t nf_conncount_locks[CONNCOUNT_SLOTS] __cacheline_aligned_in_smp; |
64 | 56 | ||
65 | struct nf_conncount_data { | 57 | struct nf_conncount_data { |
66 | unsigned int keylen; | 58 | unsigned int keylen; |
@@ -89,79 +81,25 @@ static int key_diff(const u32 *a, const u32 *b, unsigned int klen) | |||
89 | return memcmp(a, b, klen * sizeof(u32)); | 81 | return memcmp(a, b, klen * sizeof(u32)); |
90 | } | 82 | } |
91 | 83 | ||
92 | enum nf_conncount_list_add | 84 | static void conn_free(struct nf_conncount_list *list, |
93 | nf_conncount_add(struct nf_conncount_list *list, | ||
94 | const struct nf_conntrack_tuple *tuple, | ||
95 | const struct nf_conntrack_zone *zone) | ||
96 | { | ||
97 | struct nf_conncount_tuple *conn; | ||
98 | |||
99 | if (WARN_ON_ONCE(list->count > INT_MAX)) | ||
100 | return NF_CONNCOUNT_ERR; | ||
101 | |||
102 | conn = kmem_cache_alloc(conncount_conn_cachep, GFP_ATOMIC); | ||
103 | if (conn == NULL) | ||
104 | return NF_CONNCOUNT_ERR; | ||
105 | |||
106 | conn->tuple = *tuple; | ||
107 | conn->zone = *zone; | ||
108 | conn->cpu = raw_smp_processor_id(); | ||
109 | conn->jiffies32 = (u32)jiffies; | ||
110 | conn->dead = false; | ||
111 | spin_lock_bh(&list->list_lock); | ||
112 | if (list->dead == true) { | ||
113 | kmem_cache_free(conncount_conn_cachep, conn); | ||
114 | spin_unlock_bh(&list->list_lock); | ||
115 | return NF_CONNCOUNT_SKIP; | ||
116 | } | ||
117 | list_add_tail(&conn->node, &list->head); | ||
118 | list->count++; | ||
119 | spin_unlock_bh(&list->list_lock); | ||
120 | return NF_CONNCOUNT_ADDED; | ||
121 | } | ||
122 | EXPORT_SYMBOL_GPL(nf_conncount_add); | ||
123 | |||
124 | static void __conn_free(struct rcu_head *h) | ||
125 | { | ||
126 | struct nf_conncount_tuple *conn; | ||
127 | |||
128 | conn = container_of(h, struct nf_conncount_tuple, rcu_head); | ||
129 | kmem_cache_free(conncount_conn_cachep, conn); | ||
130 | } | ||
131 | |||
132 | static bool conn_free(struct nf_conncount_list *list, | ||
133 | struct nf_conncount_tuple *conn) | 85 | struct nf_conncount_tuple *conn) |
134 | { | 86 | { |
135 | bool free_entry = false; | 87 | lockdep_assert_held(&list->list_lock); |
136 | |||
137 | spin_lock_bh(&list->list_lock); | ||
138 | |||
139 | if (conn->dead) { | ||
140 | spin_unlock_bh(&list->list_lock); | ||
141 | return free_entry; | ||
142 | } | ||
143 | 88 | ||
144 | list->count--; | 89 | list->count--; |
145 | conn->dead = true; | 90 | list_del(&conn->node); |
146 | list_del_rcu(&conn->node); | ||
147 | if (list->count == 0) { | ||
148 | list->dead = true; | ||
149 | free_entry = true; | ||
150 | } | ||
151 | 91 | ||
152 | spin_unlock_bh(&list->list_lock); | 92 | kmem_cache_free(conncount_conn_cachep, conn); |
153 | call_rcu(&conn->rcu_head, __conn_free); | ||
154 | return free_entry; | ||
155 | } | 93 | } |
156 | 94 | ||
157 | static const struct nf_conntrack_tuple_hash * | 95 | static const struct nf_conntrack_tuple_hash * |
158 | find_or_evict(struct net *net, struct nf_conncount_list *list, | 96 | find_or_evict(struct net *net, struct nf_conncount_list *list, |
159 | struct nf_conncount_tuple *conn, bool *free_entry) | 97 | struct nf_conncount_tuple *conn) |
160 | { | 98 | { |
161 | const struct nf_conntrack_tuple_hash *found; | 99 | const struct nf_conntrack_tuple_hash *found; |
162 | unsigned long a, b; | 100 | unsigned long a, b; |
163 | int cpu = raw_smp_processor_id(); | 101 | int cpu = raw_smp_processor_id(); |
164 | __s32 age; | 102 | u32 age; |
165 | 103 | ||
166 | found = nf_conntrack_find_get(net, &conn->zone, &conn->tuple); | 104 | found = nf_conntrack_find_get(net, &conn->zone, &conn->tuple); |
167 | if (found) | 105 | if (found) |
@@ -176,52 +114,45 @@ find_or_evict(struct net *net, struct nf_conncount_list *list, | |||
176 | */ | 114 | */ |
177 | age = a - b; | 115 | age = a - b; |
178 | if (conn->cpu == cpu || age >= 2) { | 116 | if (conn->cpu == cpu || age >= 2) { |
179 | *free_entry = conn_free(list, conn); | 117 | conn_free(list, conn); |
180 | return ERR_PTR(-ENOENT); | 118 | return ERR_PTR(-ENOENT); |
181 | } | 119 | } |
182 | 120 | ||
183 | return ERR_PTR(-EAGAIN); | 121 | return ERR_PTR(-EAGAIN); |
184 | } | 122 | } |
185 | 123 | ||
186 | void nf_conncount_lookup(struct net *net, | 124 | static int __nf_conncount_add(struct net *net, |
187 | struct nf_conncount_list *list, | 125 | struct nf_conncount_list *list, |
188 | const struct nf_conntrack_tuple *tuple, | 126 | const struct nf_conntrack_tuple *tuple, |
189 | const struct nf_conntrack_zone *zone, | 127 | const struct nf_conntrack_zone *zone) |
190 | bool *addit) | ||
191 | { | 128 | { |
192 | const struct nf_conntrack_tuple_hash *found; | 129 | const struct nf_conntrack_tuple_hash *found; |
193 | struct nf_conncount_tuple *conn, *conn_n; | 130 | struct nf_conncount_tuple *conn, *conn_n; |
194 | struct nf_conn *found_ct; | 131 | struct nf_conn *found_ct; |
195 | unsigned int collect = 0; | 132 | unsigned int collect = 0; |
196 | bool free_entry = false; | ||
197 | |||
198 | /* best effort only */ | ||
199 | *addit = tuple ? true : false; | ||
200 | 133 | ||
201 | /* check the saved connections */ | 134 | /* check the saved connections */ |
202 | list_for_each_entry_safe(conn, conn_n, &list->head, node) { | 135 | list_for_each_entry_safe(conn, conn_n, &list->head, node) { |
203 | if (collect > CONNCOUNT_GC_MAX_NODES) | 136 | if (collect > CONNCOUNT_GC_MAX_NODES) |
204 | break; | 137 | break; |
205 | 138 | ||
206 | found = find_or_evict(net, list, conn, &free_entry); | 139 | found = find_or_evict(net, list, conn); |
207 | if (IS_ERR(found)) { | 140 | if (IS_ERR(found)) { |
208 | /* Not found, but might be about to be confirmed */ | 141 | /* Not found, but might be about to be confirmed */ |
209 | if (PTR_ERR(found) == -EAGAIN) { | 142 | if (PTR_ERR(found) == -EAGAIN) { |
210 | if (!tuple) | ||
211 | continue; | ||
212 | |||
213 | if (nf_ct_tuple_equal(&conn->tuple, tuple) && | 143 | if (nf_ct_tuple_equal(&conn->tuple, tuple) && |
214 | nf_ct_zone_id(&conn->zone, conn->zone.dir) == | 144 | nf_ct_zone_id(&conn->zone, conn->zone.dir) == |
215 | nf_ct_zone_id(zone, zone->dir)) | 145 | nf_ct_zone_id(zone, zone->dir)) |
216 | *addit = false; | 146 | return 0; /* already exists */ |
217 | } else if (PTR_ERR(found) == -ENOENT) | 147 | } else { |
218 | collect++; | 148 | collect++; |
149 | } | ||
219 | continue; | 150 | continue; |
220 | } | 151 | } |
221 | 152 | ||
222 | found_ct = nf_ct_tuplehash_to_ctrack(found); | 153 | found_ct = nf_ct_tuplehash_to_ctrack(found); |
223 | 154 | ||
224 | if (tuple && nf_ct_tuple_equal(&conn->tuple, tuple) && | 155 | if (nf_ct_tuple_equal(&conn->tuple, tuple) && |
225 | nf_ct_zone_equal(found_ct, zone, zone->dir)) { | 156 | nf_ct_zone_equal(found_ct, zone, zone->dir)) { |
226 | /* | 157 | /* |
227 | * We should not see tuples twice unless someone hooks | 158 | * We should not see tuples twice unless someone hooks |
@@ -229,7 +160,8 @@ void nf_conncount_lookup(struct net *net, | |||
229 | * | 160 | * |
230 | * Attempt to avoid a re-add in this case. | 161 | * Attempt to avoid a re-add in this case. |
231 | */ | 162 | */ |
232 | *addit = false; | 163 | nf_ct_put(found_ct); |
164 | return 0; | ||
233 | } else if (already_closed(found_ct)) { | 165 | } else if (already_closed(found_ct)) { |
234 | /* | 166 | /* |
235 | * we do not care about connections which are | 167 | * we do not care about connections which are |
@@ -243,19 +175,48 @@ void nf_conncount_lookup(struct net *net, | |||
243 | 175 | ||
244 | nf_ct_put(found_ct); | 176 | nf_ct_put(found_ct); |
245 | } | 177 | } |
178 | |||
179 | if (WARN_ON_ONCE(list->count > INT_MAX)) | ||
180 | return -EOVERFLOW; | ||
181 | |||
182 | conn = kmem_cache_alloc(conncount_conn_cachep, GFP_ATOMIC); | ||
183 | if (conn == NULL) | ||
184 | return -ENOMEM; | ||
185 | |||
186 | conn->tuple = *tuple; | ||
187 | conn->zone = *zone; | ||
188 | conn->cpu = raw_smp_processor_id(); | ||
189 | conn->jiffies32 = (u32)jiffies; | ||
190 | list_add_tail(&conn->node, &list->head); | ||
191 | list->count++; | ||
192 | return 0; | ||
246 | } | 193 | } |
247 | EXPORT_SYMBOL_GPL(nf_conncount_lookup); | 194 | |
195 | int nf_conncount_add(struct net *net, | ||
196 | struct nf_conncount_list *list, | ||
197 | const struct nf_conntrack_tuple *tuple, | ||
198 | const struct nf_conntrack_zone *zone) | ||
199 | { | ||
200 | int ret; | ||
201 | |||
202 | /* check the saved connections */ | ||
203 | spin_lock_bh(&list->list_lock); | ||
204 | ret = __nf_conncount_add(net, list, tuple, zone); | ||
205 | spin_unlock_bh(&list->list_lock); | ||
206 | |||
207 | return ret; | ||
208 | } | ||
209 | EXPORT_SYMBOL_GPL(nf_conncount_add); | ||
248 | 210 | ||
249 | void nf_conncount_list_init(struct nf_conncount_list *list) | 211 | void nf_conncount_list_init(struct nf_conncount_list *list) |
250 | { | 212 | { |
251 | spin_lock_init(&list->list_lock); | 213 | spin_lock_init(&list->list_lock); |
252 | INIT_LIST_HEAD(&list->head); | 214 | INIT_LIST_HEAD(&list->head); |
253 | list->count = 0; | 215 | list->count = 0; |
254 | list->dead = false; | ||
255 | } | 216 | } |
256 | EXPORT_SYMBOL_GPL(nf_conncount_list_init); | 217 | EXPORT_SYMBOL_GPL(nf_conncount_list_init); |
257 | 218 | ||
258 | /* Return true if the list is empty */ | 219 | /* Return true if the list is empty. Must be called with BH disabled. */ |
259 | bool nf_conncount_gc_list(struct net *net, | 220 | bool nf_conncount_gc_list(struct net *net, |
260 | struct nf_conncount_list *list) | 221 | struct nf_conncount_list *list) |
261 | { | 222 | { |
@@ -263,17 +224,17 @@ bool nf_conncount_gc_list(struct net *net, | |||
263 | struct nf_conncount_tuple *conn, *conn_n; | 224 | struct nf_conncount_tuple *conn, *conn_n; |
264 | struct nf_conn *found_ct; | 225 | struct nf_conn *found_ct; |
265 | unsigned int collected = 0; | 226 | unsigned int collected = 0; |
266 | bool free_entry = false; | ||
267 | bool ret = false; | 227 | bool ret = false; |
268 | 228 | ||
229 | /* don't bother if other cpu is already doing GC */ | ||
230 | if (!spin_trylock(&list->list_lock)) | ||
231 | return false; | ||
232 | |||
269 | list_for_each_entry_safe(conn, conn_n, &list->head, node) { | 233 | list_for_each_entry_safe(conn, conn_n, &list->head, node) { |
270 | found = find_or_evict(net, list, conn, &free_entry); | 234 | found = find_or_evict(net, list, conn); |
271 | if (IS_ERR(found)) { | 235 | if (IS_ERR(found)) { |
272 | if (PTR_ERR(found) == -ENOENT) { | 236 | if (PTR_ERR(found) == -ENOENT) |
273 | if (free_entry) | ||
274 | return true; | ||
275 | collected++; | 237 | collected++; |
276 | } | ||
277 | continue; | 238 | continue; |
278 | } | 239 | } |
279 | 240 | ||
@@ -284,23 +245,19 @@ bool nf_conncount_gc_list(struct net *net, | |||
284 | * closed already -> ditch it | 245 | * closed already -> ditch it |
285 | */ | 246 | */ |
286 | nf_ct_put(found_ct); | 247 | nf_ct_put(found_ct); |
287 | if (conn_free(list, conn)) | 248 | conn_free(list, conn); |
288 | return true; | ||
289 | collected++; | 249 | collected++; |
290 | continue; | 250 | continue; |
291 | } | 251 | } |
292 | 252 | ||
293 | nf_ct_put(found_ct); | 253 | nf_ct_put(found_ct); |
294 | if (collected > CONNCOUNT_GC_MAX_NODES) | 254 | if (collected > CONNCOUNT_GC_MAX_NODES) |
295 | return false; | 255 | break; |
296 | } | 256 | } |
297 | 257 | ||
298 | spin_lock_bh(&list->list_lock); | 258 | if (!list->count) |
299 | if (!list->count) { | ||
300 | list->dead = true; | ||
301 | ret = true; | 259 | ret = true; |
302 | } | 260 | spin_unlock(&list->list_lock); |
303 | spin_unlock_bh(&list->list_lock); | ||
304 | 261 | ||
305 | return ret; | 262 | return ret; |
306 | } | 263 | } |
@@ -314,6 +271,7 @@ static void __tree_nodes_free(struct rcu_head *h) | |||
314 | kmem_cache_free(conncount_rb_cachep, rbconn); | 271 | kmem_cache_free(conncount_rb_cachep, rbconn); |
315 | } | 272 | } |
316 | 273 | ||
274 | /* caller must hold tree nf_conncount_locks[] lock */ | ||
317 | static void tree_nodes_free(struct rb_root *root, | 275 | static void tree_nodes_free(struct rb_root *root, |
318 | struct nf_conncount_rb *gc_nodes[], | 276 | struct nf_conncount_rb *gc_nodes[], |
319 | unsigned int gc_count) | 277 | unsigned int gc_count) |
@@ -323,8 +281,10 @@ static void tree_nodes_free(struct rb_root *root, | |||
323 | while (gc_count) { | 281 | while (gc_count) { |
324 | rbconn = gc_nodes[--gc_count]; | 282 | rbconn = gc_nodes[--gc_count]; |
325 | spin_lock(&rbconn->list.list_lock); | 283 | spin_lock(&rbconn->list.list_lock); |
326 | rb_erase(&rbconn->node, root); | 284 | if (!rbconn->list.count) { |
327 | call_rcu(&rbconn->rcu_head, __tree_nodes_free); | 285 | rb_erase(&rbconn->node, root); |
286 | call_rcu(&rbconn->rcu_head, __tree_nodes_free); | ||
287 | } | ||
328 | spin_unlock(&rbconn->list.list_lock); | 288 | spin_unlock(&rbconn->list.list_lock); |
329 | } | 289 | } |
330 | } | 290 | } |
@@ -341,20 +301,19 @@ insert_tree(struct net *net, | |||
341 | struct rb_root *root, | 301 | struct rb_root *root, |
342 | unsigned int hash, | 302 | unsigned int hash, |
343 | const u32 *key, | 303 | const u32 *key, |
344 | u8 keylen, | ||
345 | const struct nf_conntrack_tuple *tuple, | 304 | const struct nf_conntrack_tuple *tuple, |
346 | const struct nf_conntrack_zone *zone) | 305 | const struct nf_conntrack_zone *zone) |
347 | { | 306 | { |
348 | enum nf_conncount_list_add ret; | ||
349 | struct nf_conncount_rb *gc_nodes[CONNCOUNT_GC_MAX_NODES]; | 307 | struct nf_conncount_rb *gc_nodes[CONNCOUNT_GC_MAX_NODES]; |
350 | struct rb_node **rbnode, *parent; | 308 | struct rb_node **rbnode, *parent; |
351 | struct nf_conncount_rb *rbconn; | 309 | struct nf_conncount_rb *rbconn; |
352 | struct nf_conncount_tuple *conn; | 310 | struct nf_conncount_tuple *conn; |
353 | unsigned int count = 0, gc_count = 0; | 311 | unsigned int count = 0, gc_count = 0; |
354 | bool node_found = false; | 312 | u8 keylen = data->keylen; |
355 | 313 | bool do_gc = true; | |
356 | spin_lock_bh(&nf_conncount_locks[hash % CONNCOUNT_LOCK_SLOTS]); | ||
357 | 314 | ||
315 | spin_lock_bh(&nf_conncount_locks[hash]); | ||
316 | restart: | ||
358 | parent = NULL; | 317 | parent = NULL; |
359 | rbnode = &(root->rb_node); | 318 | rbnode = &(root->rb_node); |
360 | while (*rbnode) { | 319 | while (*rbnode) { |
@@ -368,45 +327,32 @@ insert_tree(struct net *net, | |||
368 | } else if (diff > 0) { | 327 | } else if (diff > 0) { |
369 | rbnode = &((*rbnode)->rb_right); | 328 | rbnode = &((*rbnode)->rb_right); |
370 | } else { | 329 | } else { |
371 | /* unlikely: other cpu added node already */ | 330 | int ret; |
372 | node_found = true; | 331 | |
373 | ret = nf_conncount_add(&rbconn->list, tuple, zone); | 332 | ret = nf_conncount_add(net, &rbconn->list, tuple, zone); |
374 | if (ret == NF_CONNCOUNT_ERR) { | 333 | if (ret) |
375 | count = 0; /* hotdrop */ | 334 | count = 0; /* hotdrop */ |
376 | } else if (ret == NF_CONNCOUNT_ADDED) { | 335 | else |
377 | count = rbconn->list.count; | 336 | count = rbconn->list.count; |
378 | } else { | 337 | tree_nodes_free(root, gc_nodes, gc_count); |
379 | /* NF_CONNCOUNT_SKIP, rbconn is already | 338 | goto out_unlock; |
380 | * reclaimed by gc, insert a new tree node | ||
381 | */ | ||
382 | node_found = false; | ||
383 | } | ||
384 | break; | ||
385 | } | 339 | } |
386 | 340 | ||
387 | if (gc_count >= ARRAY_SIZE(gc_nodes)) | 341 | if (gc_count >= ARRAY_SIZE(gc_nodes)) |
388 | continue; | 342 | continue; |
389 | 343 | ||
390 | if (nf_conncount_gc_list(net, &rbconn->list)) | 344 | if (do_gc && nf_conncount_gc_list(net, &rbconn->list)) |
391 | gc_nodes[gc_count++] = rbconn; | 345 | gc_nodes[gc_count++] = rbconn; |
392 | } | 346 | } |
393 | 347 | ||
394 | if (gc_count) { | 348 | if (gc_count) { |
395 | tree_nodes_free(root, gc_nodes, gc_count); | 349 | tree_nodes_free(root, gc_nodes, gc_count); |
396 | /* tree_node_free before new allocation permits | 350 | schedule_gc_worker(data, hash); |
397 | * allocator to re-use newly free'd object. | 351 | gc_count = 0; |
398 | * | 352 | do_gc = false; |
399 | * This is a rare event; in most cases we will find | 353 | goto restart; |
400 | * existing node to re-use. (or gc_count is 0). | ||
401 | */ | ||
402 | |||
403 | if (gc_count >= ARRAY_SIZE(gc_nodes)) | ||
404 | schedule_gc_worker(data, hash); | ||
405 | } | 354 | } |
406 | 355 | ||
407 | if (node_found) | ||
408 | goto out_unlock; | ||
409 | |||
410 | /* expected case: match, insert new node */ | 356 | /* expected case: match, insert new node */ |
411 | rbconn = kmem_cache_alloc(conncount_rb_cachep, GFP_ATOMIC); | 357 | rbconn = kmem_cache_alloc(conncount_rb_cachep, GFP_ATOMIC); |
412 | if (rbconn == NULL) | 358 | if (rbconn == NULL) |
@@ -430,7 +376,7 @@ insert_tree(struct net *net, | |||
430 | rb_link_node_rcu(&rbconn->node, parent, rbnode); | 376 | rb_link_node_rcu(&rbconn->node, parent, rbnode); |
431 | rb_insert_color(&rbconn->node, root); | 377 | rb_insert_color(&rbconn->node, root); |
432 | out_unlock: | 378 | out_unlock: |
433 | spin_unlock_bh(&nf_conncount_locks[hash % CONNCOUNT_LOCK_SLOTS]); | 379 | spin_unlock_bh(&nf_conncount_locks[hash]); |
434 | return count; | 380 | return count; |
435 | } | 381 | } |
436 | 382 | ||
@@ -441,7 +387,6 @@ count_tree(struct net *net, | |||
441 | const struct nf_conntrack_tuple *tuple, | 387 | const struct nf_conntrack_tuple *tuple, |
442 | const struct nf_conntrack_zone *zone) | 388 | const struct nf_conntrack_zone *zone) |
443 | { | 389 | { |
444 | enum nf_conncount_list_add ret; | ||
445 | struct rb_root *root; | 390 | struct rb_root *root; |
446 | struct rb_node *parent; | 391 | struct rb_node *parent; |
447 | struct nf_conncount_rb *rbconn; | 392 | struct nf_conncount_rb *rbconn; |
@@ -454,7 +399,6 @@ count_tree(struct net *net, | |||
454 | parent = rcu_dereference_raw(root->rb_node); | 399 | parent = rcu_dereference_raw(root->rb_node); |
455 | while (parent) { | 400 | while (parent) { |
456 | int diff; | 401 | int diff; |
457 | bool addit; | ||
458 | 402 | ||
459 | rbconn = rb_entry(parent, struct nf_conncount_rb, node); | 403 | rbconn = rb_entry(parent, struct nf_conncount_rb, node); |
460 | 404 | ||
@@ -464,31 +408,36 @@ count_tree(struct net *net, | |||
464 | } else if (diff > 0) { | 408 | } else if (diff > 0) { |
465 | parent = rcu_dereference_raw(parent->rb_right); | 409 | parent = rcu_dereference_raw(parent->rb_right); |
466 | } else { | 410 | } else { |
467 | /* same source network -> be counted! */ | 411 | int ret; |
468 | nf_conncount_lookup(net, &rbconn->list, tuple, zone, | ||
469 | &addit); | ||
470 | 412 | ||
471 | if (!addit) | 413 | if (!tuple) { |
414 | nf_conncount_gc_list(net, &rbconn->list); | ||
472 | return rbconn->list.count; | 415 | return rbconn->list.count; |
416 | } | ||
473 | 417 | ||
474 | ret = nf_conncount_add(&rbconn->list, tuple, zone); | 418 | spin_lock_bh(&rbconn->list.list_lock); |
475 | if (ret == NF_CONNCOUNT_ERR) { | 419 | /* Node might be about to be free'd. |
476 | return 0; /* hotdrop */ | 420 | * We need to defer to insert_tree() in this case. |
477 | } else if (ret == NF_CONNCOUNT_ADDED) { | 421 | */ |
478 | return rbconn->list.count; | 422 | if (rbconn->list.count == 0) { |
479 | } else { | 423 | spin_unlock_bh(&rbconn->list.list_lock); |
480 | /* NF_CONNCOUNT_SKIP, rbconn is already | ||
481 | * reclaimed by gc, insert a new tree node | ||
482 | */ | ||
483 | break; | 424 | break; |
484 | } | 425 | } |
426 | |||
427 | /* same source network -> be counted! */ | ||
428 | ret = __nf_conncount_add(net, &rbconn->list, tuple, zone); | ||
429 | spin_unlock_bh(&rbconn->list.list_lock); | ||
430 | if (ret) | ||
431 | return 0; /* hotdrop */ | ||
432 | else | ||
433 | return rbconn->list.count; | ||
485 | } | 434 | } |
486 | } | 435 | } |
487 | 436 | ||
488 | if (!tuple) | 437 | if (!tuple) |
489 | return 0; | 438 | return 0; |
490 | 439 | ||
491 | return insert_tree(net, data, root, hash, key, keylen, tuple, zone); | 440 | return insert_tree(net, data, root, hash, key, tuple, zone); |
492 | } | 441 | } |
493 | 442 | ||
494 | static void tree_gc_worker(struct work_struct *work) | 443 | static void tree_gc_worker(struct work_struct *work) |
@@ -499,27 +448,47 @@ static void tree_gc_worker(struct work_struct *work) | |||
499 | struct rb_node *node; | 448 | struct rb_node *node; |
500 | unsigned int tree, next_tree, gc_count = 0; | 449 | unsigned int tree, next_tree, gc_count = 0; |
501 | 450 | ||
502 | tree = data->gc_tree % CONNCOUNT_LOCK_SLOTS; | 451 | tree = data->gc_tree % CONNCOUNT_SLOTS; |
503 | root = &data->root[tree]; | 452 | root = &data->root[tree]; |
504 | 453 | ||
454 | local_bh_disable(); | ||
505 | rcu_read_lock(); | 455 | rcu_read_lock(); |
506 | for (node = rb_first(root); node != NULL; node = rb_next(node)) { | 456 | for (node = rb_first(root); node != NULL; node = rb_next(node)) { |
507 | rbconn = rb_entry(node, struct nf_conncount_rb, node); | 457 | rbconn = rb_entry(node, struct nf_conncount_rb, node); |
508 | if (nf_conncount_gc_list(data->net, &rbconn->list)) | 458 | if (nf_conncount_gc_list(data->net, &rbconn->list)) |
509 | gc_nodes[gc_count++] = rbconn; | 459 | gc_count++; |
510 | } | 460 | } |
511 | rcu_read_unlock(); | 461 | rcu_read_unlock(); |
462 | local_bh_enable(); | ||
463 | |||
464 | cond_resched(); | ||
512 | 465 | ||
513 | spin_lock_bh(&nf_conncount_locks[tree]); | 466 | spin_lock_bh(&nf_conncount_locks[tree]); |
467 | if (gc_count < ARRAY_SIZE(gc_nodes)) | ||
468 | goto next; /* do not bother */ | ||
514 | 469 | ||
515 | if (gc_count) { | 470 | gc_count = 0; |
516 | tree_nodes_free(root, gc_nodes, gc_count); | 471 | node = rb_first(root); |
472 | while (node != NULL) { | ||
473 | rbconn = rb_entry(node, struct nf_conncount_rb, node); | ||
474 | node = rb_next(node); | ||
475 | |||
476 | if (rbconn->list.count > 0) | ||
477 | continue; | ||
478 | |||
479 | gc_nodes[gc_count++] = rbconn; | ||
480 | if (gc_count >= ARRAY_SIZE(gc_nodes)) { | ||
481 | tree_nodes_free(root, gc_nodes, gc_count); | ||
482 | gc_count = 0; | ||
483 | } | ||
517 | } | 484 | } |
518 | 485 | ||
486 | tree_nodes_free(root, gc_nodes, gc_count); | ||
487 | next: | ||
519 | clear_bit(tree, data->pending_trees); | 488 | clear_bit(tree, data->pending_trees); |
520 | 489 | ||
521 | next_tree = (tree + 1) % CONNCOUNT_SLOTS; | 490 | next_tree = (tree + 1) % CONNCOUNT_SLOTS; |
522 | next_tree = find_next_bit(data->pending_trees, next_tree, CONNCOUNT_SLOTS); | 491 | next_tree = find_next_bit(data->pending_trees, CONNCOUNT_SLOTS, next_tree); |
523 | 492 | ||
524 | if (next_tree < CONNCOUNT_SLOTS) { | 493 | if (next_tree < CONNCOUNT_SLOTS) { |
525 | data->gc_tree = next_tree; | 494 | data->gc_tree = next_tree; |
@@ -621,10 +590,7 @@ static int __init nf_conncount_modinit(void) | |||
621 | { | 590 | { |
622 | int i; | 591 | int i; |
623 | 592 | ||
624 | BUILD_BUG_ON(CONNCOUNT_LOCK_SLOTS > CONNCOUNT_SLOTS); | 593 | for (i = 0; i < CONNCOUNT_SLOTS; ++i) |
625 | BUILD_BUG_ON((CONNCOUNT_SLOTS % CONNCOUNT_LOCK_SLOTS) != 0); | ||
626 | |||
627 | for (i = 0; i < CONNCOUNT_LOCK_SLOTS; ++i) | ||
628 | spin_lock_init(&nf_conncount_locks[i]); | 594 | spin_lock_init(&nf_conncount_locks[i]); |
629 | 595 | ||
630 | conncount_conn_cachep = kmem_cache_create("nf_conncount_tuple", | 596 | conncount_conn_cachep = kmem_cache_create("nf_conncount_tuple", |
diff --git a/net/netfilter/nf_tables_api.c b/net/netfilter/nf_tables_api.c index fec814dace5a..2b0a93300dd7 100644 --- a/net/netfilter/nf_tables_api.c +++ b/net/netfilter/nf_tables_api.c | |||
@@ -5727,6 +5727,8 @@ static int nf_tables_fill_flowtable_info(struct sk_buff *skb, struct net *net, | |||
5727 | goto nla_put_failure; | 5727 | goto nla_put_failure; |
5728 | 5728 | ||
5729 | nest = nla_nest_start(skb, NFTA_FLOWTABLE_HOOK); | 5729 | nest = nla_nest_start(skb, NFTA_FLOWTABLE_HOOK); |
5730 | if (!nest) | ||
5731 | goto nla_put_failure; | ||
5730 | if (nla_put_be32(skb, NFTA_FLOWTABLE_HOOK_NUM, htonl(flowtable->hooknum)) || | 5732 | if (nla_put_be32(skb, NFTA_FLOWTABLE_HOOK_NUM, htonl(flowtable->hooknum)) || |
5731 | nla_put_be32(skb, NFTA_FLOWTABLE_HOOK_PRIORITY, htonl(flowtable->priority))) | 5733 | nla_put_be32(skb, NFTA_FLOWTABLE_HOOK_PRIORITY, htonl(flowtable->priority))) |
5732 | goto nla_put_failure; | 5734 | goto nla_put_failure; |
diff --git a/net/netfilter/nft_connlimit.c b/net/netfilter/nft_connlimit.c index b90d96ba4a12..af1497ab9464 100644 --- a/net/netfilter/nft_connlimit.c +++ b/net/netfilter/nft_connlimit.c | |||
@@ -30,7 +30,6 @@ static inline void nft_connlimit_do_eval(struct nft_connlimit *priv, | |||
30 | enum ip_conntrack_info ctinfo; | 30 | enum ip_conntrack_info ctinfo; |
31 | const struct nf_conn *ct; | 31 | const struct nf_conn *ct; |
32 | unsigned int count; | 32 | unsigned int count; |
33 | bool addit; | ||
34 | 33 | ||
35 | tuple_ptr = &tuple; | 34 | tuple_ptr = &tuple; |
36 | 35 | ||
@@ -44,19 +43,12 @@ static inline void nft_connlimit_do_eval(struct nft_connlimit *priv, | |||
44 | return; | 43 | return; |
45 | } | 44 | } |
46 | 45 | ||
47 | nf_conncount_lookup(nft_net(pkt), &priv->list, tuple_ptr, zone, | 46 | if (nf_conncount_add(nft_net(pkt), &priv->list, tuple_ptr, zone)) { |
48 | &addit); | ||
49 | count = priv->list.count; | ||
50 | |||
51 | if (!addit) | ||
52 | goto out; | ||
53 | |||
54 | if (nf_conncount_add(&priv->list, tuple_ptr, zone) == NF_CONNCOUNT_ERR) { | ||
55 | regs->verdict.code = NF_DROP; | 47 | regs->verdict.code = NF_DROP; |
56 | return; | 48 | return; |
57 | } | 49 | } |
58 | count++; | 50 | |
59 | out: | 51 | count = priv->list.count; |
60 | 52 | ||
61 | if ((count > priv->limit) ^ priv->invert) { | 53 | if ((count > priv->limit) ^ priv->invert) { |
62 | regs->verdict.code = NFT_BREAK; | 54 | regs->verdict.code = NFT_BREAK; |
diff --git a/net/netrom/af_netrom.c b/net/netrom/af_netrom.c index 03f37c4e64fe..1d3144d19903 100644 --- a/net/netrom/af_netrom.c +++ b/net/netrom/af_netrom.c | |||
@@ -153,7 +153,7 @@ static struct sock *nr_find_listener(ax25_address *addr) | |||
153 | sk_for_each(s, &nr_list) | 153 | sk_for_each(s, &nr_list) |
154 | if (!ax25cmp(&nr_sk(s)->source_addr, addr) && | 154 | if (!ax25cmp(&nr_sk(s)->source_addr, addr) && |
155 | s->sk_state == TCP_LISTEN) { | 155 | s->sk_state == TCP_LISTEN) { |
156 | bh_lock_sock(s); | 156 | sock_hold(s); |
157 | goto found; | 157 | goto found; |
158 | } | 158 | } |
159 | s = NULL; | 159 | s = NULL; |
@@ -174,7 +174,7 @@ static struct sock *nr_find_socket(unsigned char index, unsigned char id) | |||
174 | struct nr_sock *nr = nr_sk(s); | 174 | struct nr_sock *nr = nr_sk(s); |
175 | 175 | ||
176 | if (nr->my_index == index && nr->my_id == id) { | 176 | if (nr->my_index == index && nr->my_id == id) { |
177 | bh_lock_sock(s); | 177 | sock_hold(s); |
178 | goto found; | 178 | goto found; |
179 | } | 179 | } |
180 | } | 180 | } |
@@ -198,7 +198,7 @@ static struct sock *nr_find_peer(unsigned char index, unsigned char id, | |||
198 | 198 | ||
199 | if (nr->your_index == index && nr->your_id == id && | 199 | if (nr->your_index == index && nr->your_id == id && |
200 | !ax25cmp(&nr->dest_addr, dest)) { | 200 | !ax25cmp(&nr->dest_addr, dest)) { |
201 | bh_lock_sock(s); | 201 | sock_hold(s); |
202 | goto found; | 202 | goto found; |
203 | } | 203 | } |
204 | } | 204 | } |
@@ -224,7 +224,7 @@ static unsigned short nr_find_next_circuit(void) | |||
224 | if (i != 0 && j != 0) { | 224 | if (i != 0 && j != 0) { |
225 | if ((sk=nr_find_socket(i, j)) == NULL) | 225 | if ((sk=nr_find_socket(i, j)) == NULL) |
226 | break; | 226 | break; |
227 | bh_unlock_sock(sk); | 227 | sock_put(sk); |
228 | } | 228 | } |
229 | 229 | ||
230 | id++; | 230 | id++; |
@@ -920,6 +920,7 @@ int nr_rx_frame(struct sk_buff *skb, struct net_device *dev) | |||
920 | } | 920 | } |
921 | 921 | ||
922 | if (sk != NULL) { | 922 | if (sk != NULL) { |
923 | bh_lock_sock(sk); | ||
923 | skb_reset_transport_header(skb); | 924 | skb_reset_transport_header(skb); |
924 | 925 | ||
925 | if (frametype == NR_CONNACK && skb->len == 22) | 926 | if (frametype == NR_CONNACK && skb->len == 22) |
@@ -929,6 +930,7 @@ int nr_rx_frame(struct sk_buff *skb, struct net_device *dev) | |||
929 | 930 | ||
930 | ret = nr_process_rx_frame(sk, skb); | 931 | ret = nr_process_rx_frame(sk, skb); |
931 | bh_unlock_sock(sk); | 932 | bh_unlock_sock(sk); |
933 | sock_put(sk); | ||
932 | return ret; | 934 | return ret; |
933 | } | 935 | } |
934 | 936 | ||
@@ -960,10 +962,12 @@ int nr_rx_frame(struct sk_buff *skb, struct net_device *dev) | |||
960 | (make = nr_make_new(sk)) == NULL) { | 962 | (make = nr_make_new(sk)) == NULL) { |
961 | nr_transmit_refusal(skb, 0); | 963 | nr_transmit_refusal(skb, 0); |
962 | if (sk) | 964 | if (sk) |
963 | bh_unlock_sock(sk); | 965 | sock_put(sk); |
964 | return 0; | 966 | return 0; |
965 | } | 967 | } |
966 | 968 | ||
969 | bh_lock_sock(sk); | ||
970 | |||
967 | window = skb->data[20]; | 971 | window = skb->data[20]; |
968 | 972 | ||
969 | skb->sk = make; | 973 | skb->sk = make; |
@@ -1016,6 +1020,7 @@ int nr_rx_frame(struct sk_buff *skb, struct net_device *dev) | |||
1016 | sk->sk_data_ready(sk); | 1020 | sk->sk_data_ready(sk); |
1017 | 1021 | ||
1018 | bh_unlock_sock(sk); | 1022 | bh_unlock_sock(sk); |
1023 | sock_put(sk); | ||
1019 | 1024 | ||
1020 | nr_insert_socket(make); | 1025 | nr_insert_socket(make); |
1021 | 1026 | ||
diff --git a/net/rds/tcp.c b/net/rds/tcp.c index b9bbcf3d6c63..c16f0a362c32 100644 --- a/net/rds/tcp.c +++ b/net/rds/tcp.c | |||
@@ -623,7 +623,7 @@ static void __net_exit rds_tcp_exit_net(struct net *net) | |||
623 | if (rtn->rds_tcp_sysctl) | 623 | if (rtn->rds_tcp_sysctl) |
624 | unregister_net_sysctl_table(rtn->rds_tcp_sysctl); | 624 | unregister_net_sysctl_table(rtn->rds_tcp_sysctl); |
625 | 625 | ||
626 | if (net != &init_net && rtn->ctl_table) | 626 | if (net != &init_net) |
627 | kfree(rtn->ctl_table); | 627 | kfree(rtn->ctl_table); |
628 | } | 628 | } |
629 | 629 | ||
diff --git a/net/sunrpc/svcsock.c b/net/sunrpc/svcsock.c index c7ae1ed5324f..a6a060925e5d 100644 --- a/net/sunrpc/svcsock.c +++ b/net/sunrpc/svcsock.c | |||
@@ -542,7 +542,7 @@ static int svc_udp_recvfrom(struct svc_rqst *rqstp) | |||
542 | /* Don't enable netstamp, sunrpc doesn't | 542 | /* Don't enable netstamp, sunrpc doesn't |
543 | need that much accuracy */ | 543 | need that much accuracy */ |
544 | } | 544 | } |
545 | svsk->sk_sk->sk_stamp = skb->tstamp; | 545 | sock_write_timestamp(svsk->sk_sk, skb->tstamp); |
546 | set_bit(XPT_DATA, &svsk->sk_xprt.xpt_flags); /* there may be more data... */ | 546 | set_bit(XPT_DATA, &svsk->sk_xprt.xpt_flags); /* there may be more data... */ |
547 | 547 | ||
548 | len = skb->len; | 548 | len = skb->len; |
diff --git a/net/sunrpc/sysctl.c b/net/sunrpc/sysctl.c index 8c3936403fea..0bea8ff8b0d3 100644 --- a/net/sunrpc/sysctl.c +++ b/net/sunrpc/sysctl.c | |||
@@ -89,7 +89,7 @@ proc_dodebug(struct ctl_table *table, int write, | |||
89 | left = *lenp; | 89 | left = *lenp; |
90 | 90 | ||
91 | if (write) { | 91 | if (write) { |
92 | if (!access_ok(VERIFY_READ, buffer, left)) | 92 | if (!access_ok(buffer, left)) |
93 | return -EFAULT; | 93 | return -EFAULT; |
94 | p = buffer; | 94 | p = buffer; |
95 | while (left && __get_user(c, p) >= 0 && isspace(c)) | 95 | while (left && __get_user(c, p) >= 0 && isspace(c)) |
diff --git a/net/tipc/bearer.c b/net/tipc/bearer.c index fb2c0d8f359f..d27f30a9a01d 100644 --- a/net/tipc/bearer.c +++ b/net/tipc/bearer.c | |||
@@ -319,7 +319,6 @@ static int tipc_enable_bearer(struct net *net, const char *name, | |||
319 | res = tipc_disc_create(net, b, &b->bcast_addr, &skb); | 319 | res = tipc_disc_create(net, b, &b->bcast_addr, &skb); |
320 | if (res) { | 320 | if (res) { |
321 | bearer_disable(net, b); | 321 | bearer_disable(net, b); |
322 | kfree(b); | ||
323 | errstr = "failed to create discoverer"; | 322 | errstr = "failed to create discoverer"; |
324 | goto rejected; | 323 | goto rejected; |
325 | } | 324 | } |
diff --git a/net/tipc/netlink_compat.c b/net/tipc/netlink_compat.c index 21f6ccc89401..40f5cae623a7 100644 --- a/net/tipc/netlink_compat.c +++ b/net/tipc/netlink_compat.c | |||
@@ -904,6 +904,8 @@ static int tipc_nl_compat_publ_dump(struct tipc_nl_compat_msg *msg, u32 sock) | |||
904 | 904 | ||
905 | hdr = genlmsg_put(args, 0, 0, &tipc_genl_family, NLM_F_MULTI, | 905 | hdr = genlmsg_put(args, 0, 0, &tipc_genl_family, NLM_F_MULTI, |
906 | TIPC_NL_PUBL_GET); | 906 | TIPC_NL_PUBL_GET); |
907 | if (!hdr) | ||
908 | return -EMSGSIZE; | ||
907 | 909 | ||
908 | nest = nla_nest_start(args, TIPC_NLA_SOCK); | 910 | nest = nla_nest_start(args, TIPC_NLA_SOCK); |
909 | if (!nest) { | 911 | if (!nest) { |
diff --git a/security/tomoyo/common.c b/security/tomoyo/common.c index 9b38f94b5dd0..c598aa00d5e3 100644 --- a/security/tomoyo/common.c +++ b/security/tomoyo/common.c | |||
@@ -2591,7 +2591,7 @@ ssize_t tomoyo_write_control(struct tomoyo_io_buffer *head, | |||
2591 | int idx; | 2591 | int idx; |
2592 | if (!head->write) | 2592 | if (!head->write) |
2593 | return -ENOSYS; | 2593 | return -ENOSYS; |
2594 | if (!access_ok(VERIFY_READ, buffer, buffer_len)) | 2594 | if (!access_ok(buffer, buffer_len)) |
2595 | return -EFAULT; | 2595 | return -EFAULT; |
2596 | if (mutex_lock_interruptible(&head->io_sem)) | 2596 | if (mutex_lock_interruptible(&head->io_sem)) |
2597 | return -EINTR; | 2597 | return -EINTR; |
diff --git a/sound/core/seq/seq_clientmgr.c b/sound/core/seq/seq_clientmgr.c index 92e6524a3a9d..7d4640d1fe9f 100644 --- a/sound/core/seq/seq_clientmgr.c +++ b/sound/core/seq/seq_clientmgr.c | |||
@@ -393,7 +393,7 @@ static ssize_t snd_seq_read(struct file *file, char __user *buf, size_t count, | |||
393 | if (!(snd_seq_file_flags(file) & SNDRV_SEQ_LFLG_INPUT)) | 393 | if (!(snd_seq_file_flags(file) & SNDRV_SEQ_LFLG_INPUT)) |
394 | return -ENXIO; | 394 | return -ENXIO; |
395 | 395 | ||
396 | if (!access_ok(VERIFY_WRITE, buf, count)) | 396 | if (!access_ok(buf, count)) |
397 | return -EFAULT; | 397 | return -EFAULT; |
398 | 398 | ||
399 | /* check client structures are in place */ | 399 | /* check client structures are in place */ |
diff --git a/sound/isa/sb/emu8000_patch.c b/sound/isa/sb/emu8000_patch.c index d45a6b9d6437..3d44c358c4b3 100644 --- a/sound/isa/sb/emu8000_patch.c +++ b/sound/isa/sb/emu8000_patch.c | |||
@@ -183,10 +183,10 @@ snd_emu8000_sample_new(struct snd_emux *rec, struct snd_sf_sample *sp, | |||
183 | } | 183 | } |
184 | 184 | ||
185 | if (sp->v.mode_flags & SNDRV_SFNT_SAMPLE_8BITS) { | 185 | if (sp->v.mode_flags & SNDRV_SFNT_SAMPLE_8BITS) { |
186 | if (!access_ok(VERIFY_READ, data, sp->v.size)) | 186 | if (!access_ok(data, sp->v.size)) |
187 | return -EFAULT; | 187 | return -EFAULT; |
188 | } else { | 188 | } else { |
189 | if (!access_ok(VERIFY_READ, data, sp->v.size * 2)) | 189 | if (!access_ok(data, sp->v.size * 2)) |
190 | return -EFAULT; | 190 | return -EFAULT; |
191 | } | 191 | } |
192 | 192 | ||
diff --git a/sound/pci/hda/Kconfig b/sound/pci/hda/Kconfig index 0d38c006e182..4235907b7858 100644 --- a/sound/pci/hda/Kconfig +++ b/sound/pci/hda/Kconfig | |||
@@ -226,68 +226,6 @@ config SND_HDA_POWER_SAVE_DEFAULT | |||
226 | The default time-out value in seconds for HD-audio automatic | 226 | The default time-out value in seconds for HD-audio automatic |
227 | power-save mode. 0 means to disable the power-save mode. | 227 | power-save mode. 0 means to disable the power-save mode. |
228 | 228 | ||
229 | if SND_HDA_INTEL | ||
230 | |||
231 | # The options below should not be enabled by distributions or | ||
232 | # users. They are selected by Intel/Skylake or SOF drivers when they | ||
233 | # register for a PCI ID which is also handled by the HDAudio legacy | ||
234 | # driver. When this option is selected and the DSP is detected based on | ||
235 | # the PCI class/subclass/prog-if, the probe of the HDAudio legacy | ||
236 | # aborts. This mechanism removes the need for distributions to use | ||
237 | # blacklists. It can be bypassed with module parameters should the | ||
238 | # Intel/Skylake or SOF drivers fail to handle a specific platform. | ||
239 | |||
240 | config SND_HDA_INTEL_DSP_DETECTION_SKL | ||
241 | bool | ||
242 | help | ||
243 | This option is selected by SOF or SST drivers, not users or distros. | ||
244 | It enables DSP detection based on PCI class information for | ||
245 | Skylake machines. | ||
246 | |||
247 | config SND_HDA_INTEL_DSP_DETECTION_APL | ||
248 | bool | ||
249 | help | ||
250 | This option is selected by SOF or SST drivers, not users or distros. | ||
251 | It enables DSP detection based on PCI class information for | ||
252 | Broxton/ApolloLake machines | ||
253 | |||
254 | config SND_HDA_INTEL_DSP_DETECTION_KBL | ||
255 | bool | ||
256 | help | ||
257 | This option is selected by SOF or SST drivers, not users or distros. | ||
258 | It enables DSP detection based on PCI class information for | ||
259 | KabyLake machines | ||
260 | |||
261 | config SND_HDA_INTEL_DSP_DETECTION_GLK | ||
262 | bool | ||
263 | help | ||
264 | This option is selected by SOF or SST drivers, not users or distros. | ||
265 | It enables DSP detection based on PCI class information for | ||
266 | GeminiLake machines | ||
267 | |||
268 | config SND_HDA_INTEL_DSP_DETECTION_CNL | ||
269 | bool | ||
270 | help | ||
271 | This option is selected by SOF or SST drivers, not users or distros. | ||
272 | It enables DSP detection based on PCI class information for | ||
273 | CannonLake machines | ||
274 | |||
275 | config SND_HDA_INTEL_DSP_DETECTION_CFL | ||
276 | bool | ||
277 | help | ||
278 | This option is selected by SOF or SST drivers, not users or distros. | ||
279 | It enables DSP detection based on PCI class information for | ||
280 | CoffeeLake machines | ||
281 | |||
282 | config SND_HDA_INTEL_DSP_DETECTION_ICL | ||
283 | bool | ||
284 | help | ||
285 | This option is selected by SOF or SST drivers, not users or distros. | ||
286 | It enables DSP detection based on PCI class information for | ||
287 | IceLake machines | ||
288 | |||
289 | endif ## SND_HDA_INTEL | ||
290 | |||
291 | endif | 229 | endif |
292 | 230 | ||
293 | endmenu | 231 | endmenu |
diff --git a/sound/pci/hda/hda_controller.h b/sound/pci/hda/hda_controller.h index e0c3fcbaa028..7185ed574b41 100644 --- a/sound/pci/hda/hda_controller.h +++ b/sound/pci/hda/hda_controller.h | |||
@@ -37,7 +37,7 @@ | |||
37 | #else | 37 | #else |
38 | #define AZX_DCAPS_I915_COMPONENT 0 /* NOP */ | 38 | #define AZX_DCAPS_I915_COMPONENT 0 /* NOP */ |
39 | #endif | 39 | #endif |
40 | #define AZX_DCAPS_INTEL_SHARED (1 << 14) /* shared with ASoC */ | 40 | /* 14 unused */ |
41 | #define AZX_DCAPS_CTX_WORKAROUND (1 << 15) /* X-Fi workaround */ | 41 | #define AZX_DCAPS_CTX_WORKAROUND (1 << 15) /* X-Fi workaround */ |
42 | #define AZX_DCAPS_POSFIX_LPIB (1 << 16) /* Use LPIB as default */ | 42 | #define AZX_DCAPS_POSFIX_LPIB (1 << 16) /* Use LPIB as default */ |
43 | /* 17 unused */ | 43 | /* 17 unused */ |
diff --git a/sound/pci/hda/hda_intel.c b/sound/pci/hda/hda_intel.c index e42cc2230977..e784130ea4e0 100644 --- a/sound/pci/hda/hda_intel.c +++ b/sound/pci/hda/hda_intel.c | |||
@@ -172,9 +172,6 @@ module_param_array(beep_mode, bool, NULL, 0444); | |||
172 | MODULE_PARM_DESC(beep_mode, "Select HDA Beep registration mode " | 172 | MODULE_PARM_DESC(beep_mode, "Select HDA Beep registration mode " |
173 | "(0=off, 1=on) (default=1)."); | 173 | "(0=off, 1=on) (default=1)."); |
174 | #endif | 174 | #endif |
175 | static int skl_pci_binding; | ||
176 | module_param_named(pci_binding, skl_pci_binding, int, 0444); | ||
177 | MODULE_PARM_DESC(pci_binding, "PCI binding (0=auto, 1=only legacy, 2=only asoc"); | ||
178 | 175 | ||
179 | #ifdef CONFIG_PM | 176 | #ifdef CONFIG_PM |
180 | static int param_set_xint(const char *val, const struct kernel_param *kp); | 177 | static int param_set_xint(const char *val, const struct kernel_param *kp); |
@@ -360,7 +357,6 @@ enum { | |||
360 | AZX_DCAPS_NO_64BIT |\ | 357 | AZX_DCAPS_NO_64BIT |\ |
361 | AZX_DCAPS_4K_BDLE_BOUNDARY | AZX_DCAPS_SNOOP_OFF) | 358 | AZX_DCAPS_4K_BDLE_BOUNDARY | AZX_DCAPS_SNOOP_OFF) |
362 | 359 | ||
363 | #define AZX_DCAPS_INTEL_DSP_DETECTION(conf) (IS_ENABLED(CONFIG_SND_HDA_INTEL_DSP_DETECTION_##conf) ? AZX_DCAPS_INTEL_SHARED : 0) | ||
364 | /* | 360 | /* |
365 | * vga_switcheroo support | 361 | * vga_switcheroo support |
366 | */ | 362 | */ |
@@ -2052,28 +2048,6 @@ static int azx_probe(struct pci_dev *pci, | |||
2052 | bool schedule_probe; | 2048 | bool schedule_probe; |
2053 | int err; | 2049 | int err; |
2054 | 2050 | ||
2055 | /* check if this driver can be used on SKL+ Intel platforms */ | ||
2056 | if (pci_id->driver_data & AZX_DCAPS_INTEL_SHARED) { | ||
2057 | switch (skl_pci_binding) { | ||
2058 | case SND_SKL_PCI_BIND_AUTO: | ||
2059 | if (pci->class != 0x040300) { | ||
2060 | dev_info(&pci->dev, "The DSP is enabled on this platform, aborting probe\n"); | ||
2061 | return -ENODEV; | ||
2062 | } | ||
2063 | dev_info(&pci->dev, "No DSP detected, continuing HDaudio legacy probe\n"); | ||
2064 | break; | ||
2065 | case SND_SKL_PCI_BIND_LEGACY: | ||
2066 | dev_info(&pci->dev, "Module parameter forced binding with HDaudio legacy, bypassed detection logic\n"); | ||
2067 | break; | ||
2068 | case SND_SKL_PCI_BIND_ASOC: | ||
2069 | dev_info(&pci->dev, "Module parameter forced binding with SKL+ ASoC driver, aborting probe\n"); | ||
2070 | return -ENODEV; | ||
2071 | default: | ||
2072 | dev_err(&pci->dev, "invalid value for skl_pci_binding module parameter, ignored\n"); | ||
2073 | break; | ||
2074 | } | ||
2075 | } | ||
2076 | |||
2077 | if (dev >= SNDRV_CARDS) | 2051 | if (dev >= SNDRV_CARDS) |
2078 | return -ENODEV; | 2052 | return -ENODEV; |
2079 | if (!enable[dev]) { | 2053 | if (!enable[dev]) { |
@@ -2380,48 +2354,34 @@ static const struct pci_device_id azx_ids[] = { | |||
2380 | .driver_data = AZX_DRIVER_SKL | AZX_DCAPS_INTEL_SKYLAKE }, | 2354 | .driver_data = AZX_DRIVER_SKL | AZX_DCAPS_INTEL_SKYLAKE }, |
2381 | /* Sunrise Point-LP */ | 2355 | /* Sunrise Point-LP */ |
2382 | { PCI_DEVICE(0x8086, 0x9d70), | 2356 | { PCI_DEVICE(0x8086, 0x9d70), |
2383 | .driver_data = AZX_DRIVER_SKL | AZX_DCAPS_INTEL_SKYLAKE | | 2357 | .driver_data = AZX_DRIVER_SKL | AZX_DCAPS_INTEL_SKYLAKE }, |
2384 | AZX_DCAPS_INTEL_DSP_DETECTION(SKL) | ||
2385 | }, | ||
2386 | /* Kabylake */ | 2358 | /* Kabylake */ |
2387 | { PCI_DEVICE(0x8086, 0xa171), | 2359 | { PCI_DEVICE(0x8086, 0xa171), |
2388 | .driver_data = AZX_DRIVER_SKL | AZX_DCAPS_INTEL_SKYLAKE }, | 2360 | .driver_data = AZX_DRIVER_SKL | AZX_DCAPS_INTEL_SKYLAKE }, |
2389 | /* Kabylake-LP */ | 2361 | /* Kabylake-LP */ |
2390 | { PCI_DEVICE(0x8086, 0x9d71), | 2362 | { PCI_DEVICE(0x8086, 0x9d71), |
2391 | .driver_data = AZX_DRIVER_SKL | AZX_DCAPS_INTEL_SKYLAKE | | 2363 | .driver_data = AZX_DRIVER_SKL | AZX_DCAPS_INTEL_SKYLAKE }, |
2392 | AZX_DCAPS_INTEL_DSP_DETECTION(KBL) | ||
2393 | }, | ||
2394 | /* Kabylake-H */ | 2364 | /* Kabylake-H */ |
2395 | { PCI_DEVICE(0x8086, 0xa2f0), | 2365 | { PCI_DEVICE(0x8086, 0xa2f0), |
2396 | .driver_data = AZX_DRIVER_SKL | AZX_DCAPS_INTEL_SKYLAKE }, | 2366 | .driver_data = AZX_DRIVER_SKL | AZX_DCAPS_INTEL_SKYLAKE }, |
2397 | /* Coffelake */ | 2367 | /* Coffelake */ |
2398 | { PCI_DEVICE(0x8086, 0xa348), | 2368 | { PCI_DEVICE(0x8086, 0xa348), |
2399 | .driver_data = AZX_DRIVER_SKL | AZX_DCAPS_INTEL_SKYLAKE | | 2369 | .driver_data = AZX_DRIVER_SKL | AZX_DCAPS_INTEL_SKYLAKE}, |
2400 | AZX_DCAPS_INTEL_DSP_DETECTION(CFL) | ||
2401 | }, | ||
2402 | /* Cannonlake */ | 2370 | /* Cannonlake */ |
2403 | { PCI_DEVICE(0x8086, 0x9dc8), | 2371 | { PCI_DEVICE(0x8086, 0x9dc8), |
2404 | .driver_data = AZX_DRIVER_SKL | AZX_DCAPS_INTEL_SKYLAKE | | 2372 | .driver_data = AZX_DRIVER_SKL | AZX_DCAPS_INTEL_SKYLAKE}, |
2405 | AZX_DCAPS_INTEL_DSP_DETECTION(CNL) | ||
2406 | }, | ||
2407 | /* Icelake */ | 2373 | /* Icelake */ |
2408 | { PCI_DEVICE(0x8086, 0x34c8), | 2374 | { PCI_DEVICE(0x8086, 0x34c8), |
2409 | .driver_data = AZX_DRIVER_SKL | AZX_DCAPS_INTEL_SKYLAKE | | 2375 | .driver_data = AZX_DRIVER_SKL | AZX_DCAPS_INTEL_SKYLAKE}, |
2410 | AZX_DCAPS_INTEL_DSP_DETECTION(ICL) | ||
2411 | }, | ||
2412 | /* Broxton-P(Apollolake) */ | 2376 | /* Broxton-P(Apollolake) */ |
2413 | { PCI_DEVICE(0x8086, 0x5a98), | 2377 | { PCI_DEVICE(0x8086, 0x5a98), |
2414 | .driver_data = AZX_DRIVER_SKL | AZX_DCAPS_INTEL_BROXTON | | 2378 | .driver_data = AZX_DRIVER_SKL | AZX_DCAPS_INTEL_BROXTON }, |
2415 | AZX_DCAPS_INTEL_DSP_DETECTION(APL) | ||
2416 | }, | ||
2417 | /* Broxton-T */ | 2379 | /* Broxton-T */ |
2418 | { PCI_DEVICE(0x8086, 0x1a98), | 2380 | { PCI_DEVICE(0x8086, 0x1a98), |
2419 | .driver_data = AZX_DRIVER_SKL | AZX_DCAPS_INTEL_BROXTON }, | 2381 | .driver_data = AZX_DRIVER_SKL | AZX_DCAPS_INTEL_BROXTON }, |
2420 | /* Gemini-Lake */ | 2382 | /* Gemini-Lake */ |
2421 | { PCI_DEVICE(0x8086, 0x3198), | 2383 | { PCI_DEVICE(0x8086, 0x3198), |
2422 | .driver_data = AZX_DRIVER_SKL | AZX_DCAPS_INTEL_BROXTON | | 2384 | .driver_data = AZX_DRIVER_SKL | AZX_DCAPS_INTEL_BROXTON }, |
2423 | AZX_DCAPS_INTEL_DSP_DETECTION(GLK) | ||
2424 | }, | ||
2425 | /* Haswell */ | 2385 | /* Haswell */ |
2426 | { PCI_DEVICE(0x8086, 0x0a0c), | 2386 | { PCI_DEVICE(0x8086, 0x0a0c), |
2427 | .driver_data = AZX_DRIVER_HDMI | AZX_DCAPS_INTEL_HASWELL }, | 2387 | .driver_data = AZX_DRIVER_HDMI | AZX_DCAPS_INTEL_HASWELL }, |
diff --git a/sound/pci/hda/hda_tegra.c b/sound/pci/hda/hda_tegra.c index 83befd8d43e8..97a176d817a0 100644 --- a/sound/pci/hda/hda_tegra.c +++ b/sound/pci/hda/hda_tegra.c | |||
@@ -234,10 +234,12 @@ static int hda_tegra_suspend(struct device *dev) | |||
234 | struct snd_card *card = dev_get_drvdata(dev); | 234 | struct snd_card *card = dev_get_drvdata(dev); |
235 | struct azx *chip = card->private_data; | 235 | struct azx *chip = card->private_data; |
236 | struct hda_tegra *hda = container_of(chip, struct hda_tegra, chip); | 236 | struct hda_tegra *hda = container_of(chip, struct hda_tegra, chip); |
237 | struct hdac_bus *bus = azx_bus(chip); | ||
237 | 238 | ||
238 | snd_power_change_state(card, SNDRV_CTL_POWER_D3hot); | 239 | snd_power_change_state(card, SNDRV_CTL_POWER_D3hot); |
239 | 240 | ||
240 | azx_stop_chip(chip); | 241 | azx_stop_chip(chip); |
242 | synchronize_irq(bus->irq); | ||
241 | azx_enter_link_reset(chip); | 243 | azx_enter_link_reset(chip); |
242 | hda_tegra_disable_clocks(hda); | 244 | hda_tegra_disable_clocks(hda); |
243 | 245 | ||
diff --git a/sound/pci/hda/patch_realtek.c b/sound/pci/hda/patch_realtek.c index a4f4a9dd488d..aee4cbd29d53 100644 --- a/sound/pci/hda/patch_realtek.c +++ b/sound/pci/hda/patch_realtek.c | |||
@@ -6501,7 +6501,7 @@ static const struct hda_fixup alc269_fixups[] = { | |||
6501 | [ALC294_FIXUP_ASUS_HEADSET_MIC] = { | 6501 | [ALC294_FIXUP_ASUS_HEADSET_MIC] = { |
6502 | .type = HDA_FIXUP_PINS, | 6502 | .type = HDA_FIXUP_PINS, |
6503 | .v.pins = (const struct hda_pintbl[]) { | 6503 | .v.pins = (const struct hda_pintbl[]) { |
6504 | { 0x19, 0x01a1113c }, /* use as headset mic, without its own jack detect */ | 6504 | { 0x19, 0x01a1103c }, /* use as headset mic */ |
6505 | { } | 6505 | { } |
6506 | }, | 6506 | }, |
6507 | .chained = true, | 6507 | .chained = true, |
diff --git a/sound/soc/intel/Kconfig b/sound/soc/intel/Kconfig index 2fd1b61e8331..99a62ba409df 100644 --- a/sound/soc/intel/Kconfig +++ b/sound/soc/intel/Kconfig | |||
@@ -188,12 +188,6 @@ config SND_SOC_INTEL_SKYLAKE_COMMON | |||
188 | select SND_SOC_TOPOLOGY | 188 | select SND_SOC_TOPOLOGY |
189 | select SND_SOC_INTEL_SST | 189 | select SND_SOC_INTEL_SST |
190 | select SND_SOC_HDAC_HDA if SND_SOC_INTEL_SKYLAKE_HDAUDIO_CODEC | 190 | select SND_SOC_HDAC_HDA if SND_SOC_INTEL_SKYLAKE_HDAUDIO_CODEC |
191 | select SND_HDA_INTEL_DSP_DETECTION_SKL if SND_SOC_INTEL_SKL | ||
192 | select SND_HDA_INTEL_DSP_DETECTION_APL if SND_SOC_INTEL_APL | ||
193 | select SND_HDA_INTEL_DSP_DETECTION_KBL if SND_SOC_INTEL_KBL | ||
194 | select SND_HDA_INTEL_DSP_DETECTION_GLK if SND_SOC_INTEL_GLK | ||
195 | select SND_HDA_INTEL_DSP_DETECTION_CNL if SND_SOC_INTEL_CNL | ||
196 | select SND_HDA_INTEL_DSP_DETECTION_CFL if SND_SOC_INTEL_CFL | ||
197 | select SND_SOC_ACPI_INTEL_MATCH | 191 | select SND_SOC_ACPI_INTEL_MATCH |
198 | help | 192 | help |
199 | If you have a Intel Skylake/Broxton/ApolloLake/KabyLake/ | 193 | If you have a Intel Skylake/Broxton/ApolloLake/KabyLake/ |
diff --git a/tools/perf/util/include/asm/uaccess.h b/tools/perf/util/include/asm/uaccess.h index 6a6f4b990547..548100315710 100644 --- a/tools/perf/util/include/asm/uaccess.h +++ b/tools/perf/util/include/asm/uaccess.h | |||
@@ -10,6 +10,6 @@ | |||
10 | 10 | ||
11 | #define get_user __get_user | 11 | #define get_user __get_user |
12 | 12 | ||
13 | #define access_ok(type, addr, size) 1 | 13 | #define access_ok(addr, size) 1 |
14 | 14 | ||
15 | #endif | 15 | #endif |
diff --git a/tools/testing/selftests/bpf/test_maps.c b/tools/testing/selftests/bpf/test_maps.c index 9c79ee017df3..e2b9eee37187 100644 --- a/tools/testing/selftests/bpf/test_maps.c +++ b/tools/testing/selftests/bpf/test_maps.c | |||
@@ -510,7 +510,7 @@ static void test_devmap(int task, void *data) | |||
510 | fd = bpf_create_map(BPF_MAP_TYPE_DEVMAP, sizeof(key), sizeof(value), | 510 | fd = bpf_create_map(BPF_MAP_TYPE_DEVMAP, sizeof(key), sizeof(value), |
511 | 2, 0); | 511 | 2, 0); |
512 | if (fd < 0) { | 512 | if (fd < 0) { |
513 | printf("Failed to create arraymap '%s'!\n", strerror(errno)); | 513 | printf("Failed to create devmap '%s'!\n", strerror(errno)); |
514 | exit(1); | 514 | exit(1); |
515 | } | 515 | } |
516 | 516 | ||
diff --git a/tools/testing/selftests/bpf/test_verifier.c b/tools/testing/selftests/bpf/test_verifier.c index 33f7d38849b8..10d44446e801 100644 --- a/tools/testing/selftests/bpf/test_verifier.c +++ b/tools/testing/selftests/bpf/test_verifier.c | |||
@@ -23,6 +23,7 @@ | |||
23 | #include <stdbool.h> | 23 | #include <stdbool.h> |
24 | #include <sched.h> | 24 | #include <sched.h> |
25 | #include <limits.h> | 25 | #include <limits.h> |
26 | #include <assert.h> | ||
26 | 27 | ||
27 | #include <sys/capability.h> | 28 | #include <sys/capability.h> |
28 | 29 | ||
@@ -2577,6 +2578,7 @@ static struct bpf_test tests[] = { | |||
2577 | }, | 2578 | }, |
2578 | .result = REJECT, | 2579 | .result = REJECT, |
2579 | .errstr = "invalid stack off=-79992 size=8", | 2580 | .errstr = "invalid stack off=-79992 size=8", |
2581 | .errstr_unpriv = "R1 stack pointer arithmetic goes out of range", | ||
2580 | }, | 2582 | }, |
2581 | { | 2583 | { |
2582 | "PTR_TO_STACK store/load - out of bounds high", | 2584 | "PTR_TO_STACK store/load - out of bounds high", |
@@ -3104,6 +3106,8 @@ static struct bpf_test tests[] = { | |||
3104 | BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_0, -8), | 3106 | BPF_STX_MEM(BPF_DW, BPF_REG_1, BPF_REG_0, -8), |
3105 | BPF_EXIT_INSN(), | 3107 | BPF_EXIT_INSN(), |
3106 | }, | 3108 | }, |
3109 | .errstr_unpriv = "R1 stack pointer arithmetic goes out of range", | ||
3110 | .result_unpriv = REJECT, | ||
3107 | .result = ACCEPT, | 3111 | .result = ACCEPT, |
3108 | }, | 3112 | }, |
3109 | { | 3113 | { |
@@ -3206,6 +3210,243 @@ static struct bpf_test tests[] = { | |||
3206 | .retval_unpriv = 2, | 3210 | .retval_unpriv = 2, |
3207 | }, | 3211 | }, |
3208 | { | 3212 | { |
3213 | "PTR_TO_STACK check high 1", | ||
3214 | .insns = { | ||
3215 | BPF_MOV64_REG(BPF_REG_1, BPF_REG_10), | ||
3216 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -1), | ||
3217 | BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 42), | ||
3218 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, 0), | ||
3219 | BPF_EXIT_INSN(), | ||
3220 | }, | ||
3221 | .result = ACCEPT, | ||
3222 | .retval = 42, | ||
3223 | }, | ||
3224 | { | ||
3225 | "PTR_TO_STACK check high 2", | ||
3226 | .insns = { | ||
3227 | BPF_MOV64_REG(BPF_REG_1, BPF_REG_10), | ||
3228 | BPF_ST_MEM(BPF_B, BPF_REG_1, -1, 42), | ||
3229 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, -1), | ||
3230 | BPF_EXIT_INSN(), | ||
3231 | }, | ||
3232 | .result = ACCEPT, | ||
3233 | .retval = 42, | ||
3234 | }, | ||
3235 | { | ||
3236 | "PTR_TO_STACK check high 3", | ||
3237 | .insns = { | ||
3238 | BPF_MOV64_REG(BPF_REG_1, BPF_REG_10), | ||
3239 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 0), | ||
3240 | BPF_ST_MEM(BPF_B, BPF_REG_1, -1, 42), | ||
3241 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, -1), | ||
3242 | BPF_EXIT_INSN(), | ||
3243 | }, | ||
3244 | .errstr_unpriv = "R1 stack pointer arithmetic goes out of range", | ||
3245 | .result_unpriv = REJECT, | ||
3246 | .result = ACCEPT, | ||
3247 | .retval = 42, | ||
3248 | }, | ||
3249 | { | ||
3250 | "PTR_TO_STACK check high 4", | ||
3251 | .insns = { | ||
3252 | BPF_MOV64_REG(BPF_REG_1, BPF_REG_10), | ||
3253 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, 0), | ||
3254 | BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 42), | ||
3255 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, 0), | ||
3256 | BPF_EXIT_INSN(), | ||
3257 | }, | ||
3258 | .errstr_unpriv = "R1 stack pointer arithmetic goes out of range", | ||
3259 | .errstr = "invalid stack off=0 size=1", | ||
3260 | .result = REJECT, | ||
3261 | }, | ||
3262 | { | ||
3263 | "PTR_TO_STACK check high 5", | ||
3264 | .insns = { | ||
3265 | BPF_MOV64_REG(BPF_REG_1, BPF_REG_10), | ||
3266 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, (1 << 29) - 1), | ||
3267 | BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 42), | ||
3268 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, 0), | ||
3269 | BPF_EXIT_INSN(), | ||
3270 | }, | ||
3271 | .result = REJECT, | ||
3272 | .errstr = "invalid stack off", | ||
3273 | }, | ||
3274 | { | ||
3275 | "PTR_TO_STACK check high 6", | ||
3276 | .insns = { | ||
3277 | BPF_MOV64_REG(BPF_REG_1, BPF_REG_10), | ||
3278 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, (1 << 29) - 1), | ||
3279 | BPF_ST_MEM(BPF_B, BPF_REG_1, SHRT_MAX, 42), | ||
3280 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, SHRT_MAX), | ||
3281 | BPF_EXIT_INSN(), | ||
3282 | }, | ||
3283 | .result = REJECT, | ||
3284 | .errstr = "invalid stack off", | ||
3285 | }, | ||
3286 | { | ||
3287 | "PTR_TO_STACK check high 7", | ||
3288 | .insns = { | ||
3289 | BPF_MOV64_REG(BPF_REG_1, BPF_REG_10), | ||
3290 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, (1 << 29) - 1), | ||
3291 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, (1 << 29) - 1), | ||
3292 | BPF_ST_MEM(BPF_B, BPF_REG_1, SHRT_MAX, 42), | ||
3293 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, SHRT_MAX), | ||
3294 | BPF_EXIT_INSN(), | ||
3295 | }, | ||
3296 | .result = REJECT, | ||
3297 | .errstr_unpriv = "R1 stack pointer arithmetic goes out of range", | ||
3298 | .errstr = "fp pointer offset", | ||
3299 | }, | ||
3300 | { | ||
3301 | "PTR_TO_STACK check low 1", | ||
3302 | .insns = { | ||
3303 | BPF_MOV64_REG(BPF_REG_1, BPF_REG_10), | ||
3304 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -512), | ||
3305 | BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 42), | ||
3306 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, 0), | ||
3307 | BPF_EXIT_INSN(), | ||
3308 | }, | ||
3309 | .result = ACCEPT, | ||
3310 | .retval = 42, | ||
3311 | }, | ||
3312 | { | ||
3313 | "PTR_TO_STACK check low 2", | ||
3314 | .insns = { | ||
3315 | BPF_MOV64_REG(BPF_REG_1, BPF_REG_10), | ||
3316 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -513), | ||
3317 | BPF_ST_MEM(BPF_B, BPF_REG_1, 1, 42), | ||
3318 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, 1), | ||
3319 | BPF_EXIT_INSN(), | ||
3320 | }, | ||
3321 | .result_unpriv = REJECT, | ||
3322 | .errstr_unpriv = "R1 stack pointer arithmetic goes out of range", | ||
3323 | .result = ACCEPT, | ||
3324 | .retval = 42, | ||
3325 | }, | ||
3326 | { | ||
3327 | "PTR_TO_STACK check low 3", | ||
3328 | .insns = { | ||
3329 | BPF_MOV64_REG(BPF_REG_1, BPF_REG_10), | ||
3330 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -513), | ||
3331 | BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 42), | ||
3332 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, 0), | ||
3333 | BPF_EXIT_INSN(), | ||
3334 | }, | ||
3335 | .errstr_unpriv = "R1 stack pointer arithmetic goes out of range", | ||
3336 | .errstr = "invalid stack off=-513 size=1", | ||
3337 | .result = REJECT, | ||
3338 | }, | ||
3339 | { | ||
3340 | "PTR_TO_STACK check low 4", | ||
3341 | .insns = { | ||
3342 | BPF_MOV64_REG(BPF_REG_1, BPF_REG_10), | ||
3343 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, INT_MIN), | ||
3344 | BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 42), | ||
3345 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, 0), | ||
3346 | BPF_EXIT_INSN(), | ||
3347 | }, | ||
3348 | .result = REJECT, | ||
3349 | .errstr = "math between fp pointer", | ||
3350 | }, | ||
3351 | { | ||
3352 | "PTR_TO_STACK check low 5", | ||
3353 | .insns = { | ||
3354 | BPF_MOV64_REG(BPF_REG_1, BPF_REG_10), | ||
3355 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -((1 << 29) - 1)), | ||
3356 | BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 42), | ||
3357 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, 0), | ||
3358 | BPF_EXIT_INSN(), | ||
3359 | }, | ||
3360 | .result = REJECT, | ||
3361 | .errstr = "invalid stack off", | ||
3362 | }, | ||
3363 | { | ||
3364 | "PTR_TO_STACK check low 6", | ||
3365 | .insns = { | ||
3366 | BPF_MOV64_REG(BPF_REG_1, BPF_REG_10), | ||
3367 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -((1 << 29) - 1)), | ||
3368 | BPF_ST_MEM(BPF_B, BPF_REG_1, SHRT_MIN, 42), | ||
3369 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, SHRT_MIN), | ||
3370 | BPF_EXIT_INSN(), | ||
3371 | }, | ||
3372 | .result = REJECT, | ||
3373 | .errstr = "invalid stack off", | ||
3374 | }, | ||
3375 | { | ||
3376 | "PTR_TO_STACK check low 7", | ||
3377 | .insns = { | ||
3378 | BPF_MOV64_REG(BPF_REG_1, BPF_REG_10), | ||
3379 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -((1 << 29) - 1)), | ||
3380 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -((1 << 29) - 1)), | ||
3381 | BPF_ST_MEM(BPF_B, BPF_REG_1, SHRT_MIN, 42), | ||
3382 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, SHRT_MIN), | ||
3383 | BPF_EXIT_INSN(), | ||
3384 | }, | ||
3385 | .result = REJECT, | ||
3386 | .errstr_unpriv = "R1 stack pointer arithmetic goes out of range", | ||
3387 | .errstr = "fp pointer offset", | ||
3388 | }, | ||
3389 | { | ||
3390 | "PTR_TO_STACK mixed reg/k, 1", | ||
3391 | .insns = { | ||
3392 | BPF_MOV64_REG(BPF_REG_1, BPF_REG_10), | ||
3393 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -3), | ||
3394 | BPF_MOV64_IMM(BPF_REG_2, -3), | ||
3395 | BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_2), | ||
3396 | BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 42), | ||
3397 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, 0), | ||
3398 | BPF_EXIT_INSN(), | ||
3399 | }, | ||
3400 | .result = ACCEPT, | ||
3401 | .retval = 42, | ||
3402 | }, | ||
3403 | { | ||
3404 | "PTR_TO_STACK mixed reg/k, 2", | ||
3405 | .insns = { | ||
3406 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | ||
3407 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -16, 0), | ||
3408 | BPF_MOV64_REG(BPF_REG_1, BPF_REG_10), | ||
3409 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -3), | ||
3410 | BPF_MOV64_IMM(BPF_REG_2, -3), | ||
3411 | BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_2), | ||
3412 | BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 42), | ||
3413 | BPF_MOV64_REG(BPF_REG_5, BPF_REG_10), | ||
3414 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_5, -6), | ||
3415 | BPF_EXIT_INSN(), | ||
3416 | }, | ||
3417 | .result = ACCEPT, | ||
3418 | .retval = 42, | ||
3419 | }, | ||
3420 | { | ||
3421 | "PTR_TO_STACK mixed reg/k, 3", | ||
3422 | .insns = { | ||
3423 | BPF_MOV64_REG(BPF_REG_1, BPF_REG_10), | ||
3424 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_1, -3), | ||
3425 | BPF_MOV64_IMM(BPF_REG_2, -3), | ||
3426 | BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_2), | ||
3427 | BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 42), | ||
3428 | BPF_MOV64_REG(BPF_REG_0, BPF_REG_2), | ||
3429 | BPF_EXIT_INSN(), | ||
3430 | }, | ||
3431 | .result = ACCEPT, | ||
3432 | .retval = -3, | ||
3433 | }, | ||
3434 | { | ||
3435 | "PTR_TO_STACK reg", | ||
3436 | .insns = { | ||
3437 | BPF_MOV64_REG(BPF_REG_1, BPF_REG_10), | ||
3438 | BPF_MOV64_IMM(BPF_REG_2, -3), | ||
3439 | BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_2), | ||
3440 | BPF_ST_MEM(BPF_B, BPF_REG_1, 0, 42), | ||
3441 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, 0), | ||
3442 | BPF_EXIT_INSN(), | ||
3443 | }, | ||
3444 | .result_unpriv = REJECT, | ||
3445 | .errstr_unpriv = "invalid stack off=0 size=1", | ||
3446 | .result = ACCEPT, | ||
3447 | .retval = 42, | ||
3448 | }, | ||
3449 | { | ||
3209 | "stack pointer arithmetic", | 3450 | "stack pointer arithmetic", |
3210 | .insns = { | 3451 | .insns = { |
3211 | BPF_MOV64_IMM(BPF_REG_1, 4), | 3452 | BPF_MOV64_IMM(BPF_REG_1, 4), |
@@ -6610,6 +6851,232 @@ static struct bpf_test tests[] = { | |||
6610 | .prog_type = BPF_PROG_TYPE_TRACEPOINT, | 6851 | .prog_type = BPF_PROG_TYPE_TRACEPOINT, |
6611 | }, | 6852 | }, |
6612 | { | 6853 | { |
6854 | "map access: known scalar += value_ptr from different maps", | ||
6855 | .insns = { | ||
6856 | BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1, | ||
6857 | offsetof(struct __sk_buff, len)), | ||
6858 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | ||
6859 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), | ||
6860 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8), | ||
6861 | BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 1, 3), | ||
6862 | BPF_LD_MAP_FD(BPF_REG_1, 0), | ||
6863 | BPF_JMP_IMM(BPF_JNE, BPF_REG_0, 1, 2), | ||
6864 | BPF_LD_MAP_FD(BPF_REG_1, 0), | ||
6865 | BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, | ||
6866 | BPF_FUNC_map_lookup_elem), | ||
6867 | BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 3), | ||
6868 | BPF_MOV64_IMM(BPF_REG_1, 4), | ||
6869 | BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_0), | ||
6870 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, 0), | ||
6871 | BPF_MOV64_IMM(BPF_REG_0, 1), | ||
6872 | BPF_EXIT_INSN(), | ||
6873 | }, | ||
6874 | .fixup_map_hash_16b = { 5 }, | ||
6875 | .fixup_map_array_48b = { 8 }, | ||
6876 | .result = ACCEPT, | ||
6877 | .result_unpriv = REJECT, | ||
6878 | .errstr_unpriv = "R1 tried to add from different maps", | ||
6879 | .retval = 1, | ||
6880 | }, | ||
6881 | { | ||
6882 | "map access: value_ptr -= known scalar from different maps", | ||
6883 | .insns = { | ||
6884 | BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1, | ||
6885 | offsetof(struct __sk_buff, len)), | ||
6886 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | ||
6887 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), | ||
6888 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8), | ||
6889 | BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 1, 3), | ||
6890 | BPF_LD_MAP_FD(BPF_REG_1, 0), | ||
6891 | BPF_JMP_IMM(BPF_JNE, BPF_REG_0, 1, 2), | ||
6892 | BPF_LD_MAP_FD(BPF_REG_1, 0), | ||
6893 | BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, | ||
6894 | BPF_FUNC_map_lookup_elem), | ||
6895 | BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4), | ||
6896 | BPF_MOV64_IMM(BPF_REG_1, 4), | ||
6897 | BPF_ALU64_REG(BPF_SUB, BPF_REG_0, BPF_REG_1), | ||
6898 | BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1), | ||
6899 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_0, 0), | ||
6900 | BPF_MOV64_IMM(BPF_REG_0, 1), | ||
6901 | BPF_EXIT_INSN(), | ||
6902 | }, | ||
6903 | .fixup_map_hash_16b = { 5 }, | ||
6904 | .fixup_map_array_48b = { 8 }, | ||
6905 | .result = ACCEPT, | ||
6906 | .result_unpriv = REJECT, | ||
6907 | .errstr_unpriv = "R0 min value is outside of the array range", | ||
6908 | .retval = 1, | ||
6909 | }, | ||
6910 | { | ||
6911 | "map access: known scalar += value_ptr from different maps, but same value properties", | ||
6912 | .insns = { | ||
6913 | BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1, | ||
6914 | offsetof(struct __sk_buff, len)), | ||
6915 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | ||
6916 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), | ||
6917 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8), | ||
6918 | BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 1, 3), | ||
6919 | BPF_LD_MAP_FD(BPF_REG_1, 0), | ||
6920 | BPF_JMP_IMM(BPF_JNE, BPF_REG_0, 1, 2), | ||
6921 | BPF_LD_MAP_FD(BPF_REG_1, 0), | ||
6922 | BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, | ||
6923 | BPF_FUNC_map_lookup_elem), | ||
6924 | BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 3), | ||
6925 | BPF_MOV64_IMM(BPF_REG_1, 4), | ||
6926 | BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_0), | ||
6927 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_1, 0), | ||
6928 | BPF_MOV64_IMM(BPF_REG_0, 1), | ||
6929 | BPF_EXIT_INSN(), | ||
6930 | }, | ||
6931 | .fixup_map_hash_48b = { 5 }, | ||
6932 | .fixup_map_array_48b = { 8 }, | ||
6933 | .result = ACCEPT, | ||
6934 | .retval = 1, | ||
6935 | }, | ||
6936 | { | ||
6937 | "map access: value_ptr += known scalar, upper oob arith, test 1", | ||
6938 | .insns = { | ||
6939 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | ||
6940 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), | ||
6941 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8), | ||
6942 | BPF_LD_MAP_FD(BPF_REG_1, 0), | ||
6943 | BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, | ||
6944 | BPF_FUNC_map_lookup_elem), | ||
6945 | BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4), | ||
6946 | BPF_MOV64_IMM(BPF_REG_1, 48), | ||
6947 | BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1), | ||
6948 | BPF_ALU64_REG(BPF_SUB, BPF_REG_0, BPF_REG_1), | ||
6949 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_0, 0), | ||
6950 | BPF_MOV64_IMM(BPF_REG_0, 1), | ||
6951 | BPF_EXIT_INSN(), | ||
6952 | }, | ||
6953 | .fixup_map_array_48b = { 3 }, | ||
6954 | .result = ACCEPT, | ||
6955 | .result_unpriv = REJECT, | ||
6956 | .errstr_unpriv = "R0 pointer arithmetic of map value goes out of range", | ||
6957 | .retval = 1, | ||
6958 | }, | ||
6959 | { | ||
6960 | "map access: value_ptr += known scalar, upper oob arith, test 2", | ||
6961 | .insns = { | ||
6962 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | ||
6963 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), | ||
6964 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8), | ||
6965 | BPF_LD_MAP_FD(BPF_REG_1, 0), | ||
6966 | BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, | ||
6967 | BPF_FUNC_map_lookup_elem), | ||
6968 | BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4), | ||
6969 | BPF_MOV64_IMM(BPF_REG_1, 49), | ||
6970 | BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1), | ||
6971 | BPF_ALU64_REG(BPF_SUB, BPF_REG_0, BPF_REG_1), | ||
6972 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_0, 0), | ||
6973 | BPF_MOV64_IMM(BPF_REG_0, 1), | ||
6974 | BPF_EXIT_INSN(), | ||
6975 | }, | ||
6976 | .fixup_map_array_48b = { 3 }, | ||
6977 | .result = ACCEPT, | ||
6978 | .result_unpriv = REJECT, | ||
6979 | .errstr_unpriv = "R0 pointer arithmetic of map value goes out of range", | ||
6980 | .retval = 1, | ||
6981 | }, | ||
6982 | { | ||
6983 | "map access: value_ptr += known scalar, upper oob arith, test 3", | ||
6984 | .insns = { | ||
6985 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | ||
6986 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), | ||
6987 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8), | ||
6988 | BPF_LD_MAP_FD(BPF_REG_1, 0), | ||
6989 | BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, | ||
6990 | BPF_FUNC_map_lookup_elem), | ||
6991 | BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4), | ||
6992 | BPF_MOV64_IMM(BPF_REG_1, 47), | ||
6993 | BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1), | ||
6994 | BPF_ALU64_REG(BPF_SUB, BPF_REG_0, BPF_REG_1), | ||
6995 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_0, 0), | ||
6996 | BPF_MOV64_IMM(BPF_REG_0, 1), | ||
6997 | BPF_EXIT_INSN(), | ||
6998 | }, | ||
6999 | .fixup_map_array_48b = { 3 }, | ||
7000 | .result = ACCEPT, | ||
7001 | .result_unpriv = REJECT, | ||
7002 | .errstr_unpriv = "R0 pointer arithmetic of map value goes out of range", | ||
7003 | .retval = 1, | ||
7004 | }, | ||
7005 | { | ||
7006 | "map access: value_ptr -= known scalar, lower oob arith, test 1", | ||
7007 | .insns = { | ||
7008 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | ||
7009 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), | ||
7010 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8), | ||
7011 | BPF_LD_MAP_FD(BPF_REG_1, 0), | ||
7012 | BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, | ||
7013 | BPF_FUNC_map_lookup_elem), | ||
7014 | BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 5), | ||
7015 | BPF_MOV64_IMM(BPF_REG_1, 47), | ||
7016 | BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1), | ||
7017 | BPF_MOV64_IMM(BPF_REG_1, 48), | ||
7018 | BPF_ALU64_REG(BPF_SUB, BPF_REG_0, BPF_REG_1), | ||
7019 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_0, 0), | ||
7020 | BPF_MOV64_IMM(BPF_REG_0, 1), | ||
7021 | BPF_EXIT_INSN(), | ||
7022 | }, | ||
7023 | .fixup_map_array_48b = { 3 }, | ||
7024 | .result = REJECT, | ||
7025 | .errstr = "R0 min value is outside of the array range", | ||
7026 | .result_unpriv = REJECT, | ||
7027 | .errstr_unpriv = "R0 pointer arithmetic of map value goes out of range", | ||
7028 | }, | ||
7029 | { | ||
7030 | "map access: value_ptr -= known scalar, lower oob arith, test 2", | ||
7031 | .insns = { | ||
7032 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | ||
7033 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), | ||
7034 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8), | ||
7035 | BPF_LD_MAP_FD(BPF_REG_1, 0), | ||
7036 | BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, | ||
7037 | BPF_FUNC_map_lookup_elem), | ||
7038 | BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 7), | ||
7039 | BPF_MOV64_IMM(BPF_REG_1, 47), | ||
7040 | BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1), | ||
7041 | BPF_MOV64_IMM(BPF_REG_1, 48), | ||
7042 | BPF_ALU64_REG(BPF_SUB, BPF_REG_0, BPF_REG_1), | ||
7043 | BPF_MOV64_IMM(BPF_REG_1, 1), | ||
7044 | BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1), | ||
7045 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_0, 0), | ||
7046 | BPF_MOV64_IMM(BPF_REG_0, 1), | ||
7047 | BPF_EXIT_INSN(), | ||
7048 | }, | ||
7049 | .fixup_map_array_48b = { 3 }, | ||
7050 | .result = ACCEPT, | ||
7051 | .result_unpriv = REJECT, | ||
7052 | .errstr_unpriv = "R0 pointer arithmetic of map value goes out of range", | ||
7053 | .retval = 1, | ||
7054 | }, | ||
7055 | { | ||
7056 | "map access: value_ptr -= known scalar, lower oob arith, test 3", | ||
7057 | .insns = { | ||
7058 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | ||
7059 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), | ||
7060 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8), | ||
7061 | BPF_LD_MAP_FD(BPF_REG_1, 0), | ||
7062 | BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, | ||
7063 | BPF_FUNC_map_lookup_elem), | ||
7064 | BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 5), | ||
7065 | BPF_MOV64_IMM(BPF_REG_1, 47), | ||
7066 | BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1), | ||
7067 | BPF_MOV64_IMM(BPF_REG_1, 47), | ||
7068 | BPF_ALU64_REG(BPF_SUB, BPF_REG_0, BPF_REG_1), | ||
7069 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_0, 0), | ||
7070 | BPF_MOV64_IMM(BPF_REG_0, 1), | ||
7071 | BPF_EXIT_INSN(), | ||
7072 | }, | ||
7073 | .fixup_map_array_48b = { 3 }, | ||
7074 | .result = ACCEPT, | ||
7075 | .result_unpriv = REJECT, | ||
7076 | .errstr_unpriv = "R0 pointer arithmetic of map value goes out of range", | ||
7077 | .retval = 1, | ||
7078 | }, | ||
7079 | { | ||
6613 | "map access: known scalar += value_ptr", | 7080 | "map access: known scalar += value_ptr", |
6614 | .insns = { | 7081 | .insns = { |
6615 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | 7082 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), |
@@ -6630,7 +7097,7 @@ static struct bpf_test tests[] = { | |||
6630 | .retval = 1, | 7097 | .retval = 1, |
6631 | }, | 7098 | }, |
6632 | { | 7099 | { |
6633 | "map access: value_ptr += known scalar", | 7100 | "map access: value_ptr += known scalar, 1", |
6634 | .insns = { | 7101 | .insns = { |
6635 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | 7102 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), |
6636 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), | 7103 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), |
@@ -6650,7 +7117,113 @@ static struct bpf_test tests[] = { | |||
6650 | .retval = 1, | 7117 | .retval = 1, |
6651 | }, | 7118 | }, |
6652 | { | 7119 | { |
6653 | "map access: unknown scalar += value_ptr", | 7120 | "map access: value_ptr += known scalar, 2", |
7121 | .insns = { | ||
7122 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | ||
7123 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), | ||
7124 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8), | ||
7125 | BPF_LD_MAP_FD(BPF_REG_1, 0), | ||
7126 | BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, | ||
7127 | BPF_FUNC_map_lookup_elem), | ||
7128 | BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 3), | ||
7129 | BPF_MOV64_IMM(BPF_REG_1, 49), | ||
7130 | BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1), | ||
7131 | BPF_LDX_MEM(BPF_B, BPF_REG_1, BPF_REG_0, 0), | ||
7132 | BPF_MOV64_IMM(BPF_REG_0, 1), | ||
7133 | BPF_EXIT_INSN(), | ||
7134 | }, | ||
7135 | .fixup_map_array_48b = { 3 }, | ||
7136 | .result = REJECT, | ||
7137 | .errstr = "invalid access to map value", | ||
7138 | }, | ||
7139 | { | ||
7140 | "map access: value_ptr += known scalar, 3", | ||
7141 | .insns = { | ||
7142 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | ||
7143 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), | ||
7144 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8), | ||
7145 | BPF_LD_MAP_FD(BPF_REG_1, 0), | ||
7146 | BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, | ||
7147 | BPF_FUNC_map_lookup_elem), | ||
7148 | BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 3), | ||
7149 | BPF_MOV64_IMM(BPF_REG_1, -1), | ||
7150 | BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1), | ||
7151 | BPF_LDX_MEM(BPF_B, BPF_REG_1, BPF_REG_0, 0), | ||
7152 | BPF_MOV64_IMM(BPF_REG_0, 1), | ||
7153 | BPF_EXIT_INSN(), | ||
7154 | }, | ||
7155 | .fixup_map_array_48b = { 3 }, | ||
7156 | .result = REJECT, | ||
7157 | .errstr = "invalid access to map value", | ||
7158 | }, | ||
7159 | { | ||
7160 | "map access: value_ptr += known scalar, 4", | ||
7161 | .insns = { | ||
7162 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | ||
7163 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), | ||
7164 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8), | ||
7165 | BPF_LD_MAP_FD(BPF_REG_1, 0), | ||
7166 | BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, | ||
7167 | BPF_FUNC_map_lookup_elem), | ||
7168 | BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 7), | ||
7169 | BPF_MOV64_IMM(BPF_REG_1, 5), | ||
7170 | BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1), | ||
7171 | BPF_MOV64_IMM(BPF_REG_1, -2), | ||
7172 | BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1), | ||
7173 | BPF_MOV64_IMM(BPF_REG_1, -1), | ||
7174 | BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1), | ||
7175 | BPF_LDX_MEM(BPF_B, BPF_REG_1, BPF_REG_0, 0), | ||
7176 | BPF_MOV64_IMM(BPF_REG_0, 1), | ||
7177 | BPF_EXIT_INSN(), | ||
7178 | }, | ||
7179 | .fixup_map_array_48b = { 3 }, | ||
7180 | .result = ACCEPT, | ||
7181 | .result_unpriv = REJECT, | ||
7182 | .errstr_unpriv = "R0 pointer arithmetic of map value goes out of range", | ||
7183 | .retval = 1, | ||
7184 | }, | ||
7185 | { | ||
7186 | "map access: value_ptr += known scalar, 5", | ||
7187 | .insns = { | ||
7188 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | ||
7189 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), | ||
7190 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8), | ||
7191 | BPF_LD_MAP_FD(BPF_REG_1, 0), | ||
7192 | BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, | ||
7193 | BPF_FUNC_map_lookup_elem), | ||
7194 | BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 3), | ||
7195 | BPF_MOV64_IMM(BPF_REG_1, (6 + 1) * sizeof(int)), | ||
7196 | BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_0), | ||
7197 | BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1, 0), | ||
7198 | BPF_EXIT_INSN(), | ||
7199 | }, | ||
7200 | .fixup_map_array_48b = { 3 }, | ||
7201 | .result = ACCEPT, | ||
7202 | .retval = 0xabcdef12, | ||
7203 | }, | ||
7204 | { | ||
7205 | "map access: value_ptr += known scalar, 6", | ||
7206 | .insns = { | ||
7207 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | ||
7208 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), | ||
7209 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8), | ||
7210 | BPF_LD_MAP_FD(BPF_REG_1, 0), | ||
7211 | BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, | ||
7212 | BPF_FUNC_map_lookup_elem), | ||
7213 | BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 5), | ||
7214 | BPF_MOV64_IMM(BPF_REG_1, (3 + 1) * sizeof(int)), | ||
7215 | BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1), | ||
7216 | BPF_MOV64_IMM(BPF_REG_1, 3 * sizeof(int)), | ||
7217 | BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1), | ||
7218 | BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_0, 0), | ||
7219 | BPF_EXIT_INSN(), | ||
7220 | }, | ||
7221 | .fixup_map_array_48b = { 3 }, | ||
7222 | .result = ACCEPT, | ||
7223 | .retval = 0xabcdef12, | ||
7224 | }, | ||
7225 | { | ||
7226 | "map access: unknown scalar += value_ptr, 1", | ||
6654 | .insns = { | 7227 | .insns = { |
6655 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | 7228 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), |
6656 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), | 7229 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), |
@@ -6671,7 +7244,76 @@ static struct bpf_test tests[] = { | |||
6671 | .retval = 1, | 7244 | .retval = 1, |
6672 | }, | 7245 | }, |
6673 | { | 7246 | { |
6674 | "map access: value_ptr += unknown scalar", | 7247 | "map access: unknown scalar += value_ptr, 2", |
7248 | .insns = { | ||
7249 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | ||
7250 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), | ||
7251 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8), | ||
7252 | BPF_LD_MAP_FD(BPF_REG_1, 0), | ||
7253 | BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, | ||
7254 | BPF_FUNC_map_lookup_elem), | ||
7255 | BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4), | ||
7256 | BPF_LDX_MEM(BPF_W, BPF_REG_1, BPF_REG_0, 0), | ||
7257 | BPF_ALU64_IMM(BPF_AND, BPF_REG_1, 31), | ||
7258 | BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_0), | ||
7259 | BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1, 0), | ||
7260 | BPF_EXIT_INSN(), | ||
7261 | }, | ||
7262 | .fixup_map_array_48b = { 3 }, | ||
7263 | .result = ACCEPT, | ||
7264 | .retval = 0xabcdef12, | ||
7265 | }, | ||
7266 | { | ||
7267 | "map access: unknown scalar += value_ptr, 3", | ||
7268 | .insns = { | ||
7269 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | ||
7270 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), | ||
7271 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8), | ||
7272 | BPF_LD_MAP_FD(BPF_REG_1, 0), | ||
7273 | BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, | ||
7274 | BPF_FUNC_map_lookup_elem), | ||
7275 | BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 8), | ||
7276 | BPF_MOV64_IMM(BPF_REG_1, -1), | ||
7277 | BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1), | ||
7278 | BPF_MOV64_IMM(BPF_REG_1, 1), | ||
7279 | BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1), | ||
7280 | BPF_LDX_MEM(BPF_W, BPF_REG_1, BPF_REG_0, 0), | ||
7281 | BPF_ALU64_IMM(BPF_AND, BPF_REG_1, 31), | ||
7282 | BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_0), | ||
7283 | BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1, 0), | ||
7284 | BPF_EXIT_INSN(), | ||
7285 | }, | ||
7286 | .fixup_map_array_48b = { 3 }, | ||
7287 | .result = ACCEPT, | ||
7288 | .result_unpriv = REJECT, | ||
7289 | .errstr_unpriv = "R0 pointer arithmetic of map value goes out of range", | ||
7290 | .retval = 0xabcdef12, | ||
7291 | }, | ||
7292 | { | ||
7293 | "map access: unknown scalar += value_ptr, 4", | ||
7294 | .insns = { | ||
7295 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | ||
7296 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), | ||
7297 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8), | ||
7298 | BPF_LD_MAP_FD(BPF_REG_1, 0), | ||
7299 | BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, | ||
7300 | BPF_FUNC_map_lookup_elem), | ||
7301 | BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 6), | ||
7302 | BPF_MOV64_IMM(BPF_REG_1, 19), | ||
7303 | BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1), | ||
7304 | BPF_LDX_MEM(BPF_W, BPF_REG_1, BPF_REG_0, 0), | ||
7305 | BPF_ALU64_IMM(BPF_AND, BPF_REG_1, 31), | ||
7306 | BPF_ALU64_REG(BPF_ADD, BPF_REG_1, BPF_REG_0), | ||
7307 | BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_1, 0), | ||
7308 | BPF_EXIT_INSN(), | ||
7309 | }, | ||
7310 | .fixup_map_array_48b = { 3 }, | ||
7311 | .result = REJECT, | ||
7312 | .errstr = "R1 max value is outside of the array range", | ||
7313 | .errstr_unpriv = "R1 pointer arithmetic of map value goes out of range", | ||
7314 | }, | ||
7315 | { | ||
7316 | "map access: value_ptr += unknown scalar, 1", | ||
6675 | .insns = { | 7317 | .insns = { |
6676 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | 7318 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), |
6677 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), | 7319 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), |
@@ -6692,6 +7334,54 @@ static struct bpf_test tests[] = { | |||
6692 | .retval = 1, | 7334 | .retval = 1, |
6693 | }, | 7335 | }, |
6694 | { | 7336 | { |
7337 | "map access: value_ptr += unknown scalar, 2", | ||
7338 | .insns = { | ||
7339 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | ||
7340 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), | ||
7341 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8), | ||
7342 | BPF_LD_MAP_FD(BPF_REG_1, 0), | ||
7343 | BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, | ||
7344 | BPF_FUNC_map_lookup_elem), | ||
7345 | BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 4), | ||
7346 | BPF_LDX_MEM(BPF_W, BPF_REG_1, BPF_REG_0, 0), | ||
7347 | BPF_ALU64_IMM(BPF_AND, BPF_REG_1, 31), | ||
7348 | BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1), | ||
7349 | BPF_LDX_MEM(BPF_W, BPF_REG_0, BPF_REG_0, 0), | ||
7350 | BPF_EXIT_INSN(), | ||
7351 | }, | ||
7352 | .fixup_map_array_48b = { 3 }, | ||
7353 | .result = ACCEPT, | ||
7354 | .retval = 0xabcdef12, | ||
7355 | }, | ||
7356 | { | ||
7357 | "map access: value_ptr += unknown scalar, 3", | ||
7358 | .insns = { | ||
7359 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | ||
7360 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), | ||
7361 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8), | ||
7362 | BPF_LD_MAP_FD(BPF_REG_1, 0), | ||
7363 | BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, | ||
7364 | BPF_FUNC_map_lookup_elem), | ||
7365 | BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 11), | ||
7366 | BPF_LDX_MEM(BPF_DW, BPF_REG_1, BPF_REG_0, 0), | ||
7367 | BPF_LDX_MEM(BPF_DW, BPF_REG_2, BPF_REG_0, 8), | ||
7368 | BPF_LDX_MEM(BPF_DW, BPF_REG_3, BPF_REG_0, 16), | ||
7369 | BPF_ALU64_IMM(BPF_AND, BPF_REG_1, 0xf), | ||
7370 | BPF_ALU64_IMM(BPF_AND, BPF_REG_3, 1), | ||
7371 | BPF_ALU64_IMM(BPF_OR, BPF_REG_3, 1), | ||
7372 | BPF_JMP_REG(BPF_JGT, BPF_REG_2, BPF_REG_3, 4), | ||
7373 | BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_3), | ||
7374 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_0, 0), | ||
7375 | BPF_MOV64_IMM(BPF_REG_0, 1), | ||
7376 | BPF_EXIT_INSN(), | ||
7377 | BPF_MOV64_IMM(BPF_REG_0, 2), | ||
7378 | BPF_JMP_IMM(BPF_JA, 0, 0, -3), | ||
7379 | }, | ||
7380 | .fixup_map_array_48b = { 3 }, | ||
7381 | .result = ACCEPT, | ||
7382 | .retval = 1, | ||
7383 | }, | ||
7384 | { | ||
6695 | "map access: value_ptr += value_ptr", | 7385 | "map access: value_ptr += value_ptr", |
6696 | .insns = { | 7386 | .insns = { |
6697 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | 7387 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), |
@@ -6770,6 +7460,8 @@ static struct bpf_test tests[] = { | |||
6770 | }, | 7460 | }, |
6771 | .fixup_map_array_48b = { 3 }, | 7461 | .fixup_map_array_48b = { 3 }, |
6772 | .result = ACCEPT, | 7462 | .result = ACCEPT, |
7463 | .result_unpriv = REJECT, | ||
7464 | .errstr_unpriv = "R0 pointer arithmetic of map value goes out of range", | ||
6773 | .retval = 1, | 7465 | .retval = 1, |
6774 | }, | 7466 | }, |
6775 | { | 7467 | { |
@@ -6837,6 +7529,8 @@ static struct bpf_test tests[] = { | |||
6837 | }, | 7529 | }, |
6838 | .fixup_map_array_48b = { 3 }, | 7530 | .fixup_map_array_48b = { 3 }, |
6839 | .result = ACCEPT, | 7531 | .result = ACCEPT, |
7532 | .result_unpriv = REJECT, | ||
7533 | .errstr_unpriv = "R0 pointer arithmetic of map value goes out of range", | ||
6840 | .retval = 1, | 7534 | .retval = 1, |
6841 | }, | 7535 | }, |
6842 | { | 7536 | { |
@@ -8376,6 +9070,7 @@ static struct bpf_test tests[] = { | |||
8376 | }, | 9070 | }, |
8377 | .fixup_map_hash_8b = { 3 }, | 9071 | .fixup_map_hash_8b = { 3 }, |
8378 | .errstr = "unbounded min value", | 9072 | .errstr = "unbounded min value", |
9073 | .errstr_unpriv = "R1 has unknown scalar with mixed signed bounds", | ||
8379 | .result = REJECT, | 9074 | .result = REJECT, |
8380 | }, | 9075 | }, |
8381 | { | 9076 | { |
@@ -8400,6 +9095,7 @@ static struct bpf_test tests[] = { | |||
8400 | }, | 9095 | }, |
8401 | .fixup_map_hash_8b = { 3 }, | 9096 | .fixup_map_hash_8b = { 3 }, |
8402 | .errstr = "unbounded min value", | 9097 | .errstr = "unbounded min value", |
9098 | .errstr_unpriv = "R1 has unknown scalar with mixed signed bounds", | ||
8403 | .result = REJECT, | 9099 | .result = REJECT, |
8404 | }, | 9100 | }, |
8405 | { | 9101 | { |
@@ -8426,6 +9122,7 @@ static struct bpf_test tests[] = { | |||
8426 | }, | 9122 | }, |
8427 | .fixup_map_hash_8b = { 3 }, | 9123 | .fixup_map_hash_8b = { 3 }, |
8428 | .errstr = "unbounded min value", | 9124 | .errstr = "unbounded min value", |
9125 | .errstr_unpriv = "R8 has unknown scalar with mixed signed bounds", | ||
8429 | .result = REJECT, | 9126 | .result = REJECT, |
8430 | }, | 9127 | }, |
8431 | { | 9128 | { |
@@ -8451,6 +9148,7 @@ static struct bpf_test tests[] = { | |||
8451 | }, | 9148 | }, |
8452 | .fixup_map_hash_8b = { 3 }, | 9149 | .fixup_map_hash_8b = { 3 }, |
8453 | .errstr = "unbounded min value", | 9150 | .errstr = "unbounded min value", |
9151 | .errstr_unpriv = "R8 has unknown scalar with mixed signed bounds", | ||
8454 | .result = REJECT, | 9152 | .result = REJECT, |
8455 | }, | 9153 | }, |
8456 | { | 9154 | { |
@@ -8499,6 +9197,7 @@ static struct bpf_test tests[] = { | |||
8499 | }, | 9197 | }, |
8500 | .fixup_map_hash_8b = { 3 }, | 9198 | .fixup_map_hash_8b = { 3 }, |
8501 | .errstr = "unbounded min value", | 9199 | .errstr = "unbounded min value", |
9200 | .errstr_unpriv = "R1 has unknown scalar with mixed signed bounds", | ||
8502 | .result = REJECT, | 9201 | .result = REJECT, |
8503 | }, | 9202 | }, |
8504 | { | 9203 | { |
@@ -8570,6 +9269,7 @@ static struct bpf_test tests[] = { | |||
8570 | }, | 9269 | }, |
8571 | .fixup_map_hash_8b = { 3 }, | 9270 | .fixup_map_hash_8b = { 3 }, |
8572 | .errstr = "unbounded min value", | 9271 | .errstr = "unbounded min value", |
9272 | .errstr_unpriv = "R1 has unknown scalar with mixed signed bounds", | ||
8573 | .result = REJECT, | 9273 | .result = REJECT, |
8574 | }, | 9274 | }, |
8575 | { | 9275 | { |
@@ -8621,6 +9321,7 @@ static struct bpf_test tests[] = { | |||
8621 | }, | 9321 | }, |
8622 | .fixup_map_hash_8b = { 3 }, | 9322 | .fixup_map_hash_8b = { 3 }, |
8623 | .errstr = "unbounded min value", | 9323 | .errstr = "unbounded min value", |
9324 | .errstr_unpriv = "R1 has unknown scalar with mixed signed bounds", | ||
8624 | .result = REJECT, | 9325 | .result = REJECT, |
8625 | }, | 9326 | }, |
8626 | { | 9327 | { |
@@ -8648,6 +9349,7 @@ static struct bpf_test tests[] = { | |||
8648 | }, | 9349 | }, |
8649 | .fixup_map_hash_8b = { 3 }, | 9350 | .fixup_map_hash_8b = { 3 }, |
8650 | .errstr = "unbounded min value", | 9351 | .errstr = "unbounded min value", |
9352 | .errstr_unpriv = "R1 has unknown scalar with mixed signed bounds", | ||
8651 | .result = REJECT, | 9353 | .result = REJECT, |
8652 | }, | 9354 | }, |
8653 | { | 9355 | { |
@@ -8674,6 +9376,7 @@ static struct bpf_test tests[] = { | |||
8674 | }, | 9376 | }, |
8675 | .fixup_map_hash_8b = { 3 }, | 9377 | .fixup_map_hash_8b = { 3 }, |
8676 | .errstr = "unbounded min value", | 9378 | .errstr = "unbounded min value", |
9379 | .errstr_unpriv = "R1 has unknown scalar with mixed signed bounds", | ||
8677 | .result = REJECT, | 9380 | .result = REJECT, |
8678 | }, | 9381 | }, |
8679 | { | 9382 | { |
@@ -8703,6 +9406,7 @@ static struct bpf_test tests[] = { | |||
8703 | }, | 9406 | }, |
8704 | .fixup_map_hash_8b = { 3 }, | 9407 | .fixup_map_hash_8b = { 3 }, |
8705 | .errstr = "unbounded min value", | 9408 | .errstr = "unbounded min value", |
9409 | .errstr_unpriv = "R7 has unknown scalar with mixed signed bounds", | ||
8706 | .result = REJECT, | 9410 | .result = REJECT, |
8707 | }, | 9411 | }, |
8708 | { | 9412 | { |
@@ -8733,6 +9437,7 @@ static struct bpf_test tests[] = { | |||
8733 | }, | 9437 | }, |
8734 | .fixup_map_hash_8b = { 4 }, | 9438 | .fixup_map_hash_8b = { 4 }, |
8735 | .errstr = "unbounded min value", | 9439 | .errstr = "unbounded min value", |
9440 | .errstr_unpriv = "R1 has unknown scalar with mixed signed bounds", | ||
8736 | .result = REJECT, | 9441 | .result = REJECT, |
8737 | }, | 9442 | }, |
8738 | { | 9443 | { |
@@ -8761,6 +9466,7 @@ static struct bpf_test tests[] = { | |||
8761 | }, | 9466 | }, |
8762 | .fixup_map_hash_8b = { 3 }, | 9467 | .fixup_map_hash_8b = { 3 }, |
8763 | .errstr = "unbounded min value", | 9468 | .errstr = "unbounded min value", |
9469 | .errstr_unpriv = "R1 has unknown scalar with mixed signed bounds", | ||
8764 | .result = REJECT, | 9470 | .result = REJECT, |
8765 | .result_unpriv = REJECT, | 9471 | .result_unpriv = REJECT, |
8766 | }, | 9472 | }, |
@@ -8813,9 +9519,39 @@ static struct bpf_test tests[] = { | |||
8813 | }, | 9519 | }, |
8814 | .fixup_map_hash_8b = { 3 }, | 9520 | .fixup_map_hash_8b = { 3 }, |
8815 | .errstr = "R0 min value is negative, either use unsigned index or do a if (index >=0) check.", | 9521 | .errstr = "R0 min value is negative, either use unsigned index or do a if (index >=0) check.", |
9522 | .errstr_unpriv = "R1 has unknown scalar with mixed signed bounds", | ||
8816 | .result = REJECT, | 9523 | .result = REJECT, |
8817 | }, | 9524 | }, |
8818 | { | 9525 | { |
9526 | "check subtraction on pointers for unpriv", | ||
9527 | .insns = { | ||
9528 | BPF_MOV64_IMM(BPF_REG_0, 0), | ||
9529 | BPF_LD_MAP_FD(BPF_REG_ARG1, 0), | ||
9530 | BPF_MOV64_REG(BPF_REG_ARG2, BPF_REG_FP), | ||
9531 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_ARG2, -8), | ||
9532 | BPF_ST_MEM(BPF_DW, BPF_REG_ARG2, 0, 9), | ||
9533 | BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, | ||
9534 | BPF_FUNC_map_lookup_elem), | ||
9535 | BPF_MOV64_REG(BPF_REG_9, BPF_REG_FP), | ||
9536 | BPF_ALU64_REG(BPF_SUB, BPF_REG_9, BPF_REG_0), | ||
9537 | BPF_LD_MAP_FD(BPF_REG_ARG1, 0), | ||
9538 | BPF_MOV64_REG(BPF_REG_ARG2, BPF_REG_FP), | ||
9539 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_ARG2, -8), | ||
9540 | BPF_ST_MEM(BPF_DW, BPF_REG_ARG2, 0, 0), | ||
9541 | BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, | ||
9542 | BPF_FUNC_map_lookup_elem), | ||
9543 | BPF_JMP_IMM(BPF_JNE, BPF_REG_0, 0, 1), | ||
9544 | BPF_EXIT_INSN(), | ||
9545 | BPF_STX_MEM(BPF_DW, BPF_REG_0, BPF_REG_9, 0), | ||
9546 | BPF_MOV64_IMM(BPF_REG_0, 0), | ||
9547 | BPF_EXIT_INSN(), | ||
9548 | }, | ||
9549 | .fixup_map_hash_8b = { 1, 9 }, | ||
9550 | .result = ACCEPT, | ||
9551 | .result_unpriv = REJECT, | ||
9552 | .errstr_unpriv = "R9 pointer -= pointer prohibited", | ||
9553 | }, | ||
9554 | { | ||
8819 | "bounds check based on zero-extended MOV", | 9555 | "bounds check based on zero-extended MOV", |
8820 | .insns = { | 9556 | .insns = { |
8821 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | 9557 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), |
@@ -9146,6 +9882,36 @@ static struct bpf_test tests[] = { | |||
9146 | .result = REJECT | 9882 | .result = REJECT |
9147 | }, | 9883 | }, |
9148 | { | 9884 | { |
9885 | "bounds check after 32-bit right shift with 64-bit input", | ||
9886 | .insns = { | ||
9887 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | ||
9888 | BPF_MOV64_REG(BPF_REG_2, BPF_REG_10), | ||
9889 | BPF_ALU64_IMM(BPF_ADD, BPF_REG_2, -8), | ||
9890 | BPF_LD_MAP_FD(BPF_REG_1, 0), | ||
9891 | BPF_RAW_INSN(BPF_JMP | BPF_CALL, 0, 0, 0, | ||
9892 | BPF_FUNC_map_lookup_elem), | ||
9893 | BPF_JMP_IMM(BPF_JEQ, BPF_REG_0, 0, 6), | ||
9894 | /* r1 = 2 */ | ||
9895 | BPF_MOV64_IMM(BPF_REG_1, 2), | ||
9896 | /* r1 = 1<<32 */ | ||
9897 | BPF_ALU64_IMM(BPF_LSH, BPF_REG_1, 31), | ||
9898 | /* r1 = 0 (NOT 2!) */ | ||
9899 | BPF_ALU32_IMM(BPF_RSH, BPF_REG_1, 31), | ||
9900 | /* r1 = 0xffff'fffe (NOT 0!) */ | ||
9901 | BPF_ALU32_IMM(BPF_SUB, BPF_REG_1, 2), | ||
9902 | /* computes OOB pointer */ | ||
9903 | BPF_ALU64_REG(BPF_ADD, BPF_REG_0, BPF_REG_1), | ||
9904 | /* OOB access */ | ||
9905 | BPF_LDX_MEM(BPF_B, BPF_REG_0, BPF_REG_0, 0), | ||
9906 | /* exit */ | ||
9907 | BPF_MOV64_IMM(BPF_REG_0, 0), | ||
9908 | BPF_EXIT_INSN(), | ||
9909 | }, | ||
9910 | .fixup_map_hash_8b = { 3 }, | ||
9911 | .errstr = "R0 invalid mem access", | ||
9912 | .result = REJECT, | ||
9913 | }, | ||
9914 | { | ||
9149 | "bounds check map access with off+size signed 32bit overflow. test1", | 9915 | "bounds check map access with off+size signed 32bit overflow. test1", |
9150 | .insns = { | 9916 | .insns = { |
9151 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), | 9917 | BPF_ST_MEM(BPF_DW, BPF_REG_10, -8, 0), |
@@ -9185,6 +9951,7 @@ static struct bpf_test tests[] = { | |||
9185 | }, | 9951 | }, |
9186 | .fixup_map_hash_8b = { 3 }, | 9952 | .fixup_map_hash_8b = { 3 }, |
9187 | .errstr = "pointer offset 1073741822", | 9953 | .errstr = "pointer offset 1073741822", |
9954 | .errstr_unpriv = "R0 pointer arithmetic of map value goes out of range", | ||
9188 | .result = REJECT | 9955 | .result = REJECT |
9189 | }, | 9956 | }, |
9190 | { | 9957 | { |
@@ -9206,6 +9973,7 @@ static struct bpf_test tests[] = { | |||
9206 | }, | 9973 | }, |
9207 | .fixup_map_hash_8b = { 3 }, | 9974 | .fixup_map_hash_8b = { 3 }, |
9208 | .errstr = "pointer offset -1073741822", | 9975 | .errstr = "pointer offset -1073741822", |
9976 | .errstr_unpriv = "R0 pointer arithmetic of map value goes out of range", | ||
9209 | .result = REJECT | 9977 | .result = REJECT |
9210 | }, | 9978 | }, |
9211 | { | 9979 | { |
@@ -9377,6 +10145,7 @@ static struct bpf_test tests[] = { | |||
9377 | BPF_EXIT_INSN() | 10145 | BPF_EXIT_INSN() |
9378 | }, | 10146 | }, |
9379 | .errstr = "fp pointer offset 1073741822", | 10147 | .errstr = "fp pointer offset 1073741822", |
10148 | .errstr_unpriv = "R1 stack pointer arithmetic goes out of range", | ||
9380 | .result = REJECT | 10149 | .result = REJECT |
9381 | }, | 10150 | }, |
9382 | { | 10151 | { |
@@ -13719,6 +14488,328 @@ static struct bpf_test tests[] = { | |||
13719 | .insn_processed = 15, | 14488 | .insn_processed = 15, |
13720 | }, | 14489 | }, |
13721 | { | 14490 | { |
14491 | "masking, test out of bounds 1", | ||
14492 | .insns = { | ||
14493 | BPF_MOV32_IMM(BPF_REG_1, 5), | ||
14494 | BPF_MOV32_IMM(BPF_REG_2, 5 - 1), | ||
14495 | BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1), | ||
14496 | BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1), | ||
14497 | BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0), | ||
14498 | BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63), | ||
14499 | BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2), | ||
14500 | BPF_MOV64_REG(BPF_REG_0, BPF_REG_1), | ||
14501 | BPF_EXIT_INSN(), | ||
14502 | }, | ||
14503 | .result = ACCEPT, | ||
14504 | .retval = 0, | ||
14505 | }, | ||
14506 | { | ||
14507 | "masking, test out of bounds 2", | ||
14508 | .insns = { | ||
14509 | BPF_MOV32_IMM(BPF_REG_1, 1), | ||
14510 | BPF_MOV32_IMM(BPF_REG_2, 1 - 1), | ||
14511 | BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1), | ||
14512 | BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1), | ||
14513 | BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0), | ||
14514 | BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63), | ||
14515 | BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2), | ||
14516 | BPF_MOV64_REG(BPF_REG_0, BPF_REG_1), | ||
14517 | BPF_EXIT_INSN(), | ||
14518 | }, | ||
14519 | .result = ACCEPT, | ||
14520 | .retval = 0, | ||
14521 | }, | ||
14522 | { | ||
14523 | "masking, test out of bounds 3", | ||
14524 | .insns = { | ||
14525 | BPF_MOV32_IMM(BPF_REG_1, 0xffffffff), | ||
14526 | BPF_MOV32_IMM(BPF_REG_2, 0xffffffff - 1), | ||
14527 | BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1), | ||
14528 | BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1), | ||
14529 | BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0), | ||
14530 | BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63), | ||
14531 | BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2), | ||
14532 | BPF_MOV64_REG(BPF_REG_0, BPF_REG_1), | ||
14533 | BPF_EXIT_INSN(), | ||
14534 | }, | ||
14535 | .result = ACCEPT, | ||
14536 | .retval = 0, | ||
14537 | }, | ||
14538 | { | ||
14539 | "masking, test out of bounds 4", | ||
14540 | .insns = { | ||
14541 | BPF_MOV32_IMM(BPF_REG_1, 0xffffffff), | ||
14542 | BPF_MOV32_IMM(BPF_REG_2, 1 - 1), | ||
14543 | BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1), | ||
14544 | BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1), | ||
14545 | BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0), | ||
14546 | BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63), | ||
14547 | BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2), | ||
14548 | BPF_MOV64_REG(BPF_REG_0, BPF_REG_1), | ||
14549 | BPF_EXIT_INSN(), | ||
14550 | }, | ||
14551 | .result = ACCEPT, | ||
14552 | .retval = 0, | ||
14553 | }, | ||
14554 | { | ||
14555 | "masking, test out of bounds 5", | ||
14556 | .insns = { | ||
14557 | BPF_MOV32_IMM(BPF_REG_1, -1), | ||
14558 | BPF_MOV32_IMM(BPF_REG_2, 1 - 1), | ||
14559 | BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1), | ||
14560 | BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1), | ||
14561 | BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0), | ||
14562 | BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63), | ||
14563 | BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2), | ||
14564 | BPF_MOV64_REG(BPF_REG_0, BPF_REG_1), | ||
14565 | BPF_EXIT_INSN(), | ||
14566 | }, | ||
14567 | .result = ACCEPT, | ||
14568 | .retval = 0, | ||
14569 | }, | ||
14570 | { | ||
14571 | "masking, test out of bounds 6", | ||
14572 | .insns = { | ||
14573 | BPF_MOV32_IMM(BPF_REG_1, -1), | ||
14574 | BPF_MOV32_IMM(BPF_REG_2, 0xffffffff - 1), | ||
14575 | BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1), | ||
14576 | BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1), | ||
14577 | BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0), | ||
14578 | BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63), | ||
14579 | BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2), | ||
14580 | BPF_MOV64_REG(BPF_REG_0, BPF_REG_1), | ||
14581 | BPF_EXIT_INSN(), | ||
14582 | }, | ||
14583 | .result = ACCEPT, | ||
14584 | .retval = 0, | ||
14585 | }, | ||
14586 | { | ||
14587 | "masking, test out of bounds 7", | ||
14588 | .insns = { | ||
14589 | BPF_MOV64_IMM(BPF_REG_1, 5), | ||
14590 | BPF_MOV32_IMM(BPF_REG_2, 5 - 1), | ||
14591 | BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1), | ||
14592 | BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1), | ||
14593 | BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0), | ||
14594 | BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63), | ||
14595 | BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2), | ||
14596 | BPF_MOV64_REG(BPF_REG_0, BPF_REG_1), | ||
14597 | BPF_EXIT_INSN(), | ||
14598 | }, | ||
14599 | .result = ACCEPT, | ||
14600 | .retval = 0, | ||
14601 | }, | ||
14602 | { | ||
14603 | "masking, test out of bounds 8", | ||
14604 | .insns = { | ||
14605 | BPF_MOV64_IMM(BPF_REG_1, 1), | ||
14606 | BPF_MOV32_IMM(BPF_REG_2, 1 - 1), | ||
14607 | BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1), | ||
14608 | BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1), | ||
14609 | BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0), | ||
14610 | BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63), | ||
14611 | BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2), | ||
14612 | BPF_MOV64_REG(BPF_REG_0, BPF_REG_1), | ||
14613 | BPF_EXIT_INSN(), | ||
14614 | }, | ||
14615 | .result = ACCEPT, | ||
14616 | .retval = 0, | ||
14617 | }, | ||
14618 | { | ||
14619 | "masking, test out of bounds 9", | ||
14620 | .insns = { | ||
14621 | BPF_MOV64_IMM(BPF_REG_1, 0xffffffff), | ||
14622 | BPF_MOV32_IMM(BPF_REG_2, 0xffffffff - 1), | ||
14623 | BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1), | ||
14624 | BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1), | ||
14625 | BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0), | ||
14626 | BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63), | ||
14627 | BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2), | ||
14628 | BPF_MOV64_REG(BPF_REG_0, BPF_REG_1), | ||
14629 | BPF_EXIT_INSN(), | ||
14630 | }, | ||
14631 | .result = ACCEPT, | ||
14632 | .retval = 0, | ||
14633 | }, | ||
14634 | { | ||
14635 | "masking, test out of bounds 10", | ||
14636 | .insns = { | ||
14637 | BPF_MOV64_IMM(BPF_REG_1, 0xffffffff), | ||
14638 | BPF_MOV32_IMM(BPF_REG_2, 1 - 1), | ||
14639 | BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1), | ||
14640 | BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1), | ||
14641 | BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0), | ||
14642 | BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63), | ||
14643 | BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2), | ||
14644 | BPF_MOV64_REG(BPF_REG_0, BPF_REG_1), | ||
14645 | BPF_EXIT_INSN(), | ||
14646 | }, | ||
14647 | .result = ACCEPT, | ||
14648 | .retval = 0, | ||
14649 | }, | ||
14650 | { | ||
14651 | "masking, test out of bounds 11", | ||
14652 | .insns = { | ||
14653 | BPF_MOV64_IMM(BPF_REG_1, -1), | ||
14654 | BPF_MOV32_IMM(BPF_REG_2, 1 - 1), | ||
14655 | BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1), | ||
14656 | BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1), | ||
14657 | BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0), | ||
14658 | BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63), | ||
14659 | BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2), | ||
14660 | BPF_MOV64_REG(BPF_REG_0, BPF_REG_1), | ||
14661 | BPF_EXIT_INSN(), | ||
14662 | }, | ||
14663 | .result = ACCEPT, | ||
14664 | .retval = 0, | ||
14665 | }, | ||
14666 | { | ||
14667 | "masking, test out of bounds 12", | ||
14668 | .insns = { | ||
14669 | BPF_MOV64_IMM(BPF_REG_1, -1), | ||
14670 | BPF_MOV32_IMM(BPF_REG_2, 0xffffffff - 1), | ||
14671 | BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1), | ||
14672 | BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1), | ||
14673 | BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0), | ||
14674 | BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63), | ||
14675 | BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2), | ||
14676 | BPF_MOV64_REG(BPF_REG_0, BPF_REG_1), | ||
14677 | BPF_EXIT_INSN(), | ||
14678 | }, | ||
14679 | .result = ACCEPT, | ||
14680 | .retval = 0, | ||
14681 | }, | ||
14682 | { | ||
14683 | "masking, test in bounds 1", | ||
14684 | .insns = { | ||
14685 | BPF_MOV32_IMM(BPF_REG_1, 4), | ||
14686 | BPF_MOV32_IMM(BPF_REG_2, 5 - 1), | ||
14687 | BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1), | ||
14688 | BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1), | ||
14689 | BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0), | ||
14690 | BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63), | ||
14691 | BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2), | ||
14692 | BPF_MOV64_REG(BPF_REG_0, BPF_REG_1), | ||
14693 | BPF_EXIT_INSN(), | ||
14694 | }, | ||
14695 | .result = ACCEPT, | ||
14696 | .retval = 4, | ||
14697 | }, | ||
14698 | { | ||
14699 | "masking, test in bounds 2", | ||
14700 | .insns = { | ||
14701 | BPF_MOV32_IMM(BPF_REG_1, 0), | ||
14702 | BPF_MOV32_IMM(BPF_REG_2, 0xffffffff - 1), | ||
14703 | BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1), | ||
14704 | BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1), | ||
14705 | BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0), | ||
14706 | BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63), | ||
14707 | BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2), | ||
14708 | BPF_MOV64_REG(BPF_REG_0, BPF_REG_1), | ||
14709 | BPF_EXIT_INSN(), | ||
14710 | }, | ||
14711 | .result = ACCEPT, | ||
14712 | .retval = 0, | ||
14713 | }, | ||
14714 | { | ||
14715 | "masking, test in bounds 3", | ||
14716 | .insns = { | ||
14717 | BPF_MOV32_IMM(BPF_REG_1, 0xfffffffe), | ||
14718 | BPF_MOV32_IMM(BPF_REG_2, 0xffffffff - 1), | ||
14719 | BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1), | ||
14720 | BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1), | ||
14721 | BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0), | ||
14722 | BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63), | ||
14723 | BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2), | ||
14724 | BPF_MOV64_REG(BPF_REG_0, BPF_REG_1), | ||
14725 | BPF_EXIT_INSN(), | ||
14726 | }, | ||
14727 | .result = ACCEPT, | ||
14728 | .retval = 0xfffffffe, | ||
14729 | }, | ||
14730 | { | ||
14731 | "masking, test in bounds 4", | ||
14732 | .insns = { | ||
14733 | BPF_MOV32_IMM(BPF_REG_1, 0xabcde), | ||
14734 | BPF_MOV32_IMM(BPF_REG_2, 0xabcdef - 1), | ||
14735 | BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1), | ||
14736 | BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1), | ||
14737 | BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0), | ||
14738 | BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63), | ||
14739 | BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2), | ||
14740 | BPF_MOV64_REG(BPF_REG_0, BPF_REG_1), | ||
14741 | BPF_EXIT_INSN(), | ||
14742 | }, | ||
14743 | .result = ACCEPT, | ||
14744 | .retval = 0xabcde, | ||
14745 | }, | ||
14746 | { | ||
14747 | "masking, test in bounds 5", | ||
14748 | .insns = { | ||
14749 | BPF_MOV32_IMM(BPF_REG_1, 0), | ||
14750 | BPF_MOV32_IMM(BPF_REG_2, 1 - 1), | ||
14751 | BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1), | ||
14752 | BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1), | ||
14753 | BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0), | ||
14754 | BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63), | ||
14755 | BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2), | ||
14756 | BPF_MOV64_REG(BPF_REG_0, BPF_REG_1), | ||
14757 | BPF_EXIT_INSN(), | ||
14758 | }, | ||
14759 | .result = ACCEPT, | ||
14760 | .retval = 0, | ||
14761 | }, | ||
14762 | { | ||
14763 | "masking, test in bounds 6", | ||
14764 | .insns = { | ||
14765 | BPF_MOV32_IMM(BPF_REG_1, 46), | ||
14766 | BPF_MOV32_IMM(BPF_REG_2, 47 - 1), | ||
14767 | BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_1), | ||
14768 | BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_1), | ||
14769 | BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0), | ||
14770 | BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63), | ||
14771 | BPF_ALU64_REG(BPF_AND, BPF_REG_1, BPF_REG_2), | ||
14772 | BPF_MOV64_REG(BPF_REG_0, BPF_REG_1), | ||
14773 | BPF_EXIT_INSN(), | ||
14774 | }, | ||
14775 | .result = ACCEPT, | ||
14776 | .retval = 46, | ||
14777 | }, | ||
14778 | { | ||
14779 | "masking, test in bounds 7", | ||
14780 | .insns = { | ||
14781 | BPF_MOV64_IMM(BPF_REG_3, -46), | ||
14782 | BPF_ALU64_IMM(BPF_MUL, BPF_REG_3, -1), | ||
14783 | BPF_MOV32_IMM(BPF_REG_2, 47 - 1), | ||
14784 | BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_3), | ||
14785 | BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_3), | ||
14786 | BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0), | ||
14787 | BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63), | ||
14788 | BPF_ALU64_REG(BPF_AND, BPF_REG_3, BPF_REG_2), | ||
14789 | BPF_MOV64_REG(BPF_REG_0, BPF_REG_3), | ||
14790 | BPF_EXIT_INSN(), | ||
14791 | }, | ||
14792 | .result = ACCEPT, | ||
14793 | .retval = 46, | ||
14794 | }, | ||
14795 | { | ||
14796 | "masking, test in bounds 8", | ||
14797 | .insns = { | ||
14798 | BPF_MOV64_IMM(BPF_REG_3, -47), | ||
14799 | BPF_ALU64_IMM(BPF_MUL, BPF_REG_3, -1), | ||
14800 | BPF_MOV32_IMM(BPF_REG_2, 47 - 1), | ||
14801 | BPF_ALU64_REG(BPF_SUB, BPF_REG_2, BPF_REG_3), | ||
14802 | BPF_ALU64_REG(BPF_OR, BPF_REG_2, BPF_REG_3), | ||
14803 | BPF_ALU64_IMM(BPF_NEG, BPF_REG_2, 0), | ||
14804 | BPF_ALU64_IMM(BPF_ARSH, BPF_REG_2, 63), | ||
14805 | BPF_ALU64_REG(BPF_AND, BPF_REG_3, BPF_REG_2), | ||
14806 | BPF_MOV64_REG(BPF_REG_0, BPF_REG_3), | ||
14807 | BPF_EXIT_INSN(), | ||
14808 | }, | ||
14809 | .result = ACCEPT, | ||
14810 | .retval = 0, | ||
14811 | }, | ||
14812 | { | ||
13722 | "reference tracking in call: free reference in subprog and outside", | 14813 | "reference tracking in call: free reference in subprog and outside", |
13723 | .insns = { | 14814 | .insns = { |
13724 | BPF_SK_LOOKUP, | 14815 | BPF_SK_LOOKUP, |
@@ -14413,6 +15504,16 @@ static int create_map(uint32_t type, uint32_t size_key, | |||
14413 | return fd; | 15504 | return fd; |
14414 | } | 15505 | } |
14415 | 15506 | ||
15507 | static void update_map(int fd, int index) | ||
15508 | { | ||
15509 | struct test_val value = { | ||
15510 | .index = (6 + 1) * sizeof(int), | ||
15511 | .foo[6] = 0xabcdef12, | ||
15512 | }; | ||
15513 | |||
15514 | assert(!bpf_map_update_elem(fd, &index, &value, 0)); | ||
15515 | } | ||
15516 | |||
14416 | static int create_prog_dummy1(enum bpf_prog_type prog_type) | 15517 | static int create_prog_dummy1(enum bpf_prog_type prog_type) |
14417 | { | 15518 | { |
14418 | struct bpf_insn prog[] = { | 15519 | struct bpf_insn prog[] = { |
@@ -14564,6 +15665,7 @@ static void do_test_fixup(struct bpf_test *test, enum bpf_prog_type prog_type, | |||
14564 | if (*fixup_map_array_48b) { | 15665 | if (*fixup_map_array_48b) { |
14565 | map_fds[3] = create_map(BPF_MAP_TYPE_ARRAY, sizeof(int), | 15666 | map_fds[3] = create_map(BPF_MAP_TYPE_ARRAY, sizeof(int), |
14566 | sizeof(struct test_val), 1); | 15667 | sizeof(struct test_val), 1); |
15668 | update_map(map_fds[3], 0); | ||
14567 | do { | 15669 | do { |
14568 | prog[*fixup_map_array_48b].imm = map_fds[3]; | 15670 | prog[*fixup_map_array_48b].imm = map_fds[3]; |
14569 | fixup_map_array_48b++; | 15671 | fixup_map_array_48b++; |
diff --git a/virt/kvm/kvm_main.c b/virt/kvm/kvm_main.c index 666d0155662d..1f888a103f78 100644 --- a/virt/kvm/kvm_main.c +++ b/virt/kvm/kvm_main.c | |||
@@ -939,8 +939,7 @@ int __kvm_set_memory_region(struct kvm *kvm, | |||
939 | /* We can read the guest memory with __xxx_user() later on. */ | 939 | /* We can read the guest memory with __xxx_user() later on. */ |
940 | if ((id < KVM_USER_MEM_SLOTS) && | 940 | if ((id < KVM_USER_MEM_SLOTS) && |
941 | ((mem->userspace_addr & (PAGE_SIZE - 1)) || | 941 | ((mem->userspace_addr & (PAGE_SIZE - 1)) || |
942 | !access_ok(VERIFY_WRITE, | 942 | !access_ok((void __user *)(unsigned long)mem->userspace_addr, |
943 | (void __user *)(unsigned long)mem->userspace_addr, | ||
944 | mem->memory_size))) | 943 | mem->memory_size))) |
945 | goto out; | 944 | goto out; |
946 | if (as_id >= KVM_ADDRESS_SPACE_NUM || id >= KVM_MEM_SLOTS_NUM) | 945 | if (as_id >= KVM_ADDRESS_SPACE_NUM || id >= KVM_MEM_SLOTS_NUM) |