locks.c (320424c7d44f54c18df9812fd7c45f6963524002) | locks.c (f7e33bdbd6d1bdf9c3df8bba5abcf3399f957ac3) |
---|---|
1// SPDX-License-Identifier: GPL-2.0-only 2/* 3 * linux/fs/locks.c 4 * 5 * Provide support for fcntl()'s F_GETLK, F_SETLK, and F_SETLKW calls. 6 * Doug Evans (dje@spiff.uucp), August 07, 1992 7 * 8 * Deadlock detection added. --- 1383 unchanged lines hidden (view full) --- 1392 list_empty(&fl->fl_blocked_member)); 1393 if (error) 1394 break; 1395 } 1396 locks_delete_block(fl); 1397 return error; 1398} 1399 | 1// SPDX-License-Identifier: GPL-2.0-only 2/* 3 * linux/fs/locks.c 4 * 5 * Provide support for fcntl()'s F_GETLK, F_SETLK, and F_SETLKW calls. 6 * Doug Evans (dje@spiff.uucp), August 07, 1992 7 * 8 * Deadlock detection added. --- 1383 unchanged lines hidden (view full) --- 1392 list_empty(&fl->fl_blocked_member)); 1393 if (error) 1394 break; 1395 } 1396 locks_delete_block(fl); 1397 return error; 1398} 1399 |
1400#ifdef CONFIG_MANDATORY_FILE_LOCKING 1401/** 1402 * locks_mandatory_locked - Check for an active lock 1403 * @file: the file to check 1404 * 1405 * Searches the inode's list of locks to find any POSIX locks which conflict. 1406 * This function is called from locks_verify_locked() only. 1407 */ 1408int locks_mandatory_locked(struct file *file) 1409{ 1410 int ret; 1411 struct inode *inode = locks_inode(file); 1412 struct file_lock_context *ctx; 1413 struct file_lock *fl; 1414 1415 ctx = smp_load_acquire(&inode->i_flctx); 1416 if (!ctx || list_empty_careful(&ctx->flc_posix)) 1417 return 0; 1418 1419 /* 1420 * Search the lock list for this inode for any POSIX locks. 1421 */ 1422 spin_lock(&ctx->flc_lock); 1423 ret = 0; 1424 list_for_each_entry(fl, &ctx->flc_posix, fl_list) { 1425 if (fl->fl_owner != current->files && 1426 fl->fl_owner != file) { 1427 ret = -EAGAIN; 1428 break; 1429 } 1430 } 1431 spin_unlock(&ctx->flc_lock); 1432 return ret; 1433} 1434 1435/** 1436 * locks_mandatory_area - Check for a conflicting lock 1437 * @inode: the file to check 1438 * @filp: how the file was opened (if it was) 1439 * @start: first byte in the file to check 1440 * @end: lastbyte in the file to check 1441 * @type: %F_WRLCK for a write lock, else %F_RDLCK 1442 * 1443 * Searches the inode's list of locks to find any POSIX locks which conflict. 1444 */ 1445int locks_mandatory_area(struct inode *inode, struct file *filp, loff_t start, 1446 loff_t end, unsigned char type) 1447{ 1448 struct file_lock fl; 1449 int error; 1450 bool sleep = false; 1451 1452 locks_init_lock(&fl); 1453 fl.fl_pid = current->tgid; 1454 fl.fl_file = filp; 1455 fl.fl_flags = FL_POSIX | FL_ACCESS; 1456 if (filp && !(filp->f_flags & O_NONBLOCK)) 1457 sleep = true; 1458 fl.fl_type = type; 1459 fl.fl_start = start; 1460 fl.fl_end = end; 1461 1462 for (;;) { 1463 if (filp) { 1464 fl.fl_owner = filp; 1465 fl.fl_flags &= ~FL_SLEEP; 1466 error = posix_lock_inode(inode, &fl, NULL); 1467 if (!error) 1468 break; 1469 } 1470 1471 if (sleep) 1472 fl.fl_flags |= FL_SLEEP; 1473 fl.fl_owner = current->files; 1474 error = posix_lock_inode(inode, &fl, NULL); 1475 if (error != FILE_LOCK_DEFERRED) 1476 break; 1477 error = wait_event_interruptible(fl.fl_wait, 1478 list_empty(&fl.fl_blocked_member)); 1479 if (!error) { 1480 /* 1481 * If we've been sleeping someone might have 1482 * changed the permissions behind our back. 1483 */ 1484 if (__mandatory_lock(inode)) 1485 continue; 1486 } 1487 1488 break; 1489 } 1490 locks_delete_block(&fl); 1491 1492 return error; 1493} 1494EXPORT_SYMBOL(locks_mandatory_area); 1495#endif /* CONFIG_MANDATORY_FILE_LOCKING */ 1496 | |
1497static void lease_clear_pending(struct file_lock *fl, int arg) 1498{ 1499 switch (arg) { 1500 case F_UNLCK: 1501 fl->fl_flags &= ~FL_UNLOCK_PENDING; 1502 fallthrough; 1503 case F_RDLCK: 1504 fl->fl_flags &= ~FL_DOWNGRADE_PENDING; --- 976 unchanged lines hidden (view full) --- 2481 struct file_lock *file_lock = locks_alloc_lock(); 2482 struct inode *inode = locks_inode(filp); 2483 struct file *f; 2484 int error; 2485 2486 if (file_lock == NULL) 2487 return -ENOLCK; 2488 | 1400static void lease_clear_pending(struct file_lock *fl, int arg) 1401{ 1402 switch (arg) { 1403 case F_UNLCK: 1404 fl->fl_flags &= ~FL_UNLOCK_PENDING; 1405 fallthrough; 1406 case F_RDLCK: 1407 fl->fl_flags &= ~FL_DOWNGRADE_PENDING; --- 976 unchanged lines hidden (view full) --- 2384 struct file_lock *file_lock = locks_alloc_lock(); 2385 struct inode *inode = locks_inode(filp); 2386 struct file *f; 2387 int error; 2388 2389 if (file_lock == NULL) 2390 return -ENOLCK; 2391 |
2489 /* Don't allow mandatory locks on files that may be memory mapped 2490 * and shared. 2491 */ 2492 if (mandatory_lock(inode) && mapping_writably_mapped(filp->f_mapping)) { 2493 error = -EAGAIN; 2494 goto out; 2495 } 2496 | |
2497 error = flock_to_posix_lock(filp, file_lock, flock); 2498 if (error) 2499 goto out; 2500 2501 error = check_fmode_for_setlk(file_lock); 2502 if (error) 2503 goto out; 2504 --- 101 unchanged lines hidden (view full) --- 2606 2607/* Apply the lock described by l to an open file descriptor. 2608 * This implements both the F_SETLK and F_SETLKW commands of fcntl(). 2609 */ 2610int fcntl_setlk64(unsigned int fd, struct file *filp, unsigned int cmd, 2611 struct flock64 *flock) 2612{ 2613 struct file_lock *file_lock = locks_alloc_lock(); | 2392 error = flock_to_posix_lock(filp, file_lock, flock); 2393 if (error) 2394 goto out; 2395 2396 error = check_fmode_for_setlk(file_lock); 2397 if (error) 2398 goto out; 2399 --- 101 unchanged lines hidden (view full) --- 2501 2502/* Apply the lock described by l to an open file descriptor. 2503 * This implements both the F_SETLK and F_SETLKW commands of fcntl(). 2504 */ 2505int fcntl_setlk64(unsigned int fd, struct file *filp, unsigned int cmd, 2506 struct flock64 *flock) 2507{ 2508 struct file_lock *file_lock = locks_alloc_lock(); |
2614 struct inode *inode = locks_inode(filp); | |
2615 struct file *f; 2616 int error; 2617 2618 if (file_lock == NULL) 2619 return -ENOLCK; 2620 | 2509 struct file *f; 2510 int error; 2511 2512 if (file_lock == NULL) 2513 return -ENOLCK; 2514 |
2621 /* Don't allow mandatory locks on files that may be memory mapped 2622 * and shared. 2623 */ 2624 if (mandatory_lock(inode) && mapping_writably_mapped(filp->f_mapping)) { 2625 error = -EAGAIN; 2626 goto out; 2627 } 2628 | |
2629 error = flock64_to_posix_lock(filp, file_lock, flock); 2630 if (error) 2631 goto out; 2632 2633 error = check_fmode_for_setlk(file_lock); 2634 if (error) 2635 goto out; 2636 --- 215 unchanged lines hidden (view full) --- 2852 if (fl->fl_flags & FL_ACCESS) 2853 seq_puts(f, "ACCESS"); 2854 else if (IS_OFDLCK(fl)) 2855 seq_puts(f, "OFDLCK"); 2856 else 2857 seq_puts(f, "POSIX "); 2858 2859 seq_printf(f, " %s ", | 2515 error = flock64_to_posix_lock(filp, file_lock, flock); 2516 if (error) 2517 goto out; 2518 2519 error = check_fmode_for_setlk(file_lock); 2520 if (error) 2521 goto out; 2522 --- 215 unchanged lines hidden (view full) --- 2738 if (fl->fl_flags & FL_ACCESS) 2739 seq_puts(f, "ACCESS"); 2740 else if (IS_OFDLCK(fl)) 2741 seq_puts(f, "OFDLCK"); 2742 else 2743 seq_puts(f, "POSIX "); 2744 2745 seq_printf(f, " %s ", |
2860 (inode == NULL) ? "*NOINODE*" : 2861 mandatory_lock(inode) ? "MANDATORY" : "ADVISORY "); | 2746 (inode == NULL) ? "*NOINODE*" : "ADVISORY "); |
2862 } else if (IS_FLOCK(fl)) { 2863 if (fl->fl_type & LOCK_MAND) { 2864 seq_puts(f, "FLOCK MSNFS "); 2865 } else { 2866 seq_puts(f, "FLOCK ADVISORY "); 2867 } 2868 } else if (IS_LEASE(fl)) { 2869 if (fl->fl_flags & FL_DELEG) --- 205 unchanged lines hidden --- | 2747 } else if (IS_FLOCK(fl)) { 2748 if (fl->fl_type & LOCK_MAND) { 2749 seq_puts(f, "FLOCK MSNFS "); 2750 } else { 2751 seq_puts(f, "FLOCK ADVISORY "); 2752 } 2753 } else if (IS_LEASE(fl)) { 2754 if (fl->fl_flags & FL_DELEG) --- 205 unchanged lines hidden --- |