Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

Merge tag 'ceph-for-5.14-rc1' of git://github.com/ceph/ceph-client

Pull ceph updates from Ilya Dryomov:
"We have new filesystem client metrics for reporting I/O sizes from
Xiubo, two patchsets from Jeff that begin to untangle some heavyweight
blocking locks in the filesystem and a bunch of code cleanups"

* tag 'ceph-for-5.14-rc1' of git://github.com/ceph/ceph-client:
ceph: take reference to req->r_parent at point of assignment
ceph: eliminate ceph_async_iput()
ceph: don't take s_mutex in ceph_flush_snaps
ceph: don't take s_mutex in try_flush_caps
ceph: don't take s_mutex or snap_rwsem in ceph_check_caps
ceph: eliminate session->s_gen_ttl_lock
ceph: allow ceph_put_mds_session to take NULL or ERR_PTR
ceph: clean up locking annotation for ceph_get_snap_realm and __lookup_snap_realm
ceph: add some lockdep assertions around snaprealm handling
ceph: decoding error in ceph_update_snap_realm should return -EIO
ceph: add IO size metrics support
ceph: update and rename __update_latency helper to __update_stdev
ceph: simplify the metrics struct
libceph: fix doc warnings in cls_lock_client.c
libceph: remove unnecessary ret variable in ceph_auth_init()
libceph: fix some spelling mistakes
libceph: kill ceph_none_authorizer::reply_buf
ceph: make ceph_queue_cap_snap static
ceph: make ceph_netfs_read_ops static
ceph: remove bogus checks and WARN_ONs from ceph_set_page_dirty

+312 -352
+10 -16
fs/ceph/addr.c
··· 82 82 struct inode *inode; 83 83 struct ceph_inode_info *ci; 84 84 struct ceph_snap_context *snapc; 85 - int ret; 86 - 87 - if (unlikely(!mapping)) 88 - return !TestSetPageDirty(page); 89 85 90 86 if (PageDirty(page)) { 91 87 dout("%p set_page_dirty %p idx %lu -- already dirty\n", ··· 126 130 BUG_ON(PagePrivate(page)); 127 131 attach_page_private(page, snapc); 128 132 129 - ret = __set_page_dirty_nobuffers(page); 130 - WARN_ON(!PageLocked(page)); 131 - WARN_ON(!page->mapping); 132 - 133 - return ret; 133 + return __set_page_dirty_nobuffers(page); 134 134 } 135 135 136 136 /* ··· 218 226 int err = req->r_result; 219 227 220 228 ceph_update_read_metrics(&fsc->mdsc->metric, req->r_start_latency, 221 - req->r_end_latency, err); 229 + req->r_end_latency, osd_data->length, err); 222 230 223 231 dout("%s: result %d subreq->len=%zu i_size=%lld\n", __func__, req->r_result, 224 232 subreq->len, i_size_read(req->r_inode)); ··· 305 313 ceph_put_cap_refs(ci, got); 306 314 } 307 315 308 - const struct netfs_read_request_ops ceph_netfs_read_ops = { 316 + static const struct netfs_read_request_ops ceph_netfs_read_ops = { 309 317 .init_rreq = ceph_init_rreq, 310 318 .is_cache_enabled = ceph_is_cache_enabled, 311 319 .begin_cache_operation = ceph_begin_cache_operation, ··· 552 560 err = ceph_osdc_wait_request(osdc, req); 553 561 554 562 ceph_update_write_metrics(&fsc->mdsc->metric, req->r_start_latency, 555 - req->r_end_latency, err); 563 + req->r_end_latency, len, err); 556 564 557 565 ceph_osdc_put_request(req); 558 566 if (err == 0) ··· 627 635 struct ceph_snap_context *snapc = req->r_snapc; 628 636 struct address_space *mapping = inode->i_mapping; 629 637 struct ceph_fs_client *fsc = ceph_inode_to_client(inode); 638 + unsigned int len = 0; 630 639 bool remove_page; 631 640 632 641 dout("writepages_finish %p rc %d\n", inode, rc); ··· 639 646 } else { 640 647 ceph_clear_error_write(ci); 641 648 } 642 - 643 - ceph_update_write_metrics(&fsc->mdsc->metric, req->r_start_latency, 644 - req->r_end_latency, rc); 645 649 646 650 /* 647 651 * We lost the cache cap, need to truncate the page before ··· 656 666 657 667 osd_data = osd_req_op_extent_osd_data(req, i); 658 668 BUG_ON(osd_data->type != CEPH_OSD_DATA_TYPE_PAGES); 669 + len += osd_data->length; 659 670 num_pages = calc_pages_for((u64)osd_data->alignment, 660 671 (u64)osd_data->length); 661 672 total_pages += num_pages; ··· 686 695 687 696 release_pages(osd_data->pages, num_pages); 688 697 } 698 + 699 + ceph_update_write_metrics(&fsc->mdsc->metric, req->r_start_latency, 700 + req->r_end_latency, len, rc); 689 701 690 702 ceph_put_wrbuffer_cap_refs(ci, total_pages, snapc); 691 703 ··· 1705 1711 err = ceph_osdc_wait_request(&fsc->client->osdc, req); 1706 1712 1707 1713 ceph_update_write_metrics(&fsc->mdsc->metric, req->r_start_latency, 1708 - req->r_end_latency, err); 1714 + req->r_end_latency, len, err); 1709 1715 1710 1716 out_put: 1711 1717 ceph_osdc_put_request(req);
+25 -100
fs/ceph/caps.c
··· 645 645 dout("add_cap %p mds%d cap %llx %s seq %d\n", inode, 646 646 session->s_mds, cap_id, ceph_cap_string(issued), seq); 647 647 648 - spin_lock(&session->s_gen_ttl_lock); 649 - gen = session->s_cap_gen; 650 - spin_unlock(&session->s_gen_ttl_lock); 648 + gen = atomic_read(&session->s_cap_gen); 651 649 652 650 cap = __get_cap_for_mds(ci, mds); 653 651 if (!cap) { ··· 783 785 unsigned long ttl; 784 786 u32 gen; 785 787 786 - spin_lock(&cap->session->s_gen_ttl_lock); 787 - gen = cap->session->s_cap_gen; 788 + gen = atomic_read(&cap->session->s_cap_gen); 788 789 ttl = cap->session->s_cap_ttl; 789 - spin_unlock(&cap->session->s_gen_ttl_lock); 790 790 791 791 if (cap->cap_gen < gen || time_after_eq(jiffies, ttl)) { 792 792 dout("__cap_is_valid %p cap %p issued %s " ··· 1178 1182 * s_cap_gen while session is in the reconnect state. 1179 1183 */ 1180 1184 if (queue_release && 1181 - (!session->s_cap_reconnect || cap->cap_gen == session->s_cap_gen)) { 1185 + (!session->s_cap_reconnect || 1186 + cap->cap_gen == atomic_read(&session->s_cap_gen))) { 1182 1187 cap->queue_release = 1; 1183 1188 if (removed) { 1184 1189 __ceph_queue_cap_release(session, cap); ··· 1531 1534 * asynchronously back to the MDS once sync writes complete and dirty 1532 1535 * data is written out. 1533 1536 * 1534 - * Called under i_ceph_lock. Takes s_mutex as needed. 1537 + * Called under i_ceph_lock. 1535 1538 */ 1536 1539 static void __ceph_flush_snaps(struct ceph_inode_info *ci, 1537 1540 struct ceph_mds_session *session) ··· 1653 1656 mds = ci->i_auth_cap->session->s_mds; 1654 1657 if (session && session->s_mds != mds) { 1655 1658 dout(" oops, wrong session %p mutex\n", session); 1656 - mutex_unlock(&session->s_mutex); 1657 1659 ceph_put_mds_session(session); 1658 1660 session = NULL; 1659 1661 } ··· 1661 1665 mutex_lock(&mdsc->mutex); 1662 1666 session = __ceph_lookup_mds_session(mdsc, mds); 1663 1667 mutex_unlock(&mdsc->mutex); 1664 - if (session) { 1665 - dout(" inverting session/ino locks on %p\n", session); 1666 - mutex_lock(&session->s_mutex); 1667 - } 1668 1668 goto retry; 1669 1669 } 1670 1670 ··· 1672 1680 out: 1673 1681 spin_unlock(&ci->i_ceph_lock); 1674 1682 1675 - if (psession) { 1683 + if (psession) 1676 1684 *psession = session; 1677 - } else if (session) { 1678 - mutex_unlock(&session->s_mutex); 1685 + else 1679 1686 ceph_put_mds_session(session); 1680 - } 1681 1687 /* we flushed them all; remove this inode from the queue */ 1682 1688 spin_lock(&mdsc->snap_flush_lock); 1683 1689 list_del_init(&ci->i_snap_flush_item); ··· 1905 1915 struct ceph_cap *cap; 1906 1916 u64 flush_tid, oldest_flush_tid; 1907 1917 int file_wanted, used, cap_used; 1908 - int took_snap_rwsem = 0; /* true if mdsc->snap_rwsem held */ 1909 1918 int issued, implemented, want, retain, revoking, flushing = 0; 1910 1919 int mds = -1; /* keep track of how far we've gone through i_caps list 1911 1920 to avoid an infinite loop on retry */ ··· 1912 1923 bool queue_invalidate = false; 1913 1924 bool tried_invalidate = false; 1914 1925 1926 + if (session) 1927 + ceph_get_mds_session(session); 1928 + 1915 1929 spin_lock(&ci->i_ceph_lock); 1916 1930 if (ci->i_ceph_flags & CEPH_I_FLUSH) 1917 1931 flags |= CHECK_CAPS_FLUSH; 1918 - 1919 - goto retry_locked; 1920 1932 retry: 1921 - spin_lock(&ci->i_ceph_lock); 1922 - retry_locked: 1923 1933 /* Caps wanted by virtue of active open files. */ 1924 1934 file_wanted = __ceph_caps_file_wanted(ci); 1925 1935 ··· 1998 2010 ci->i_rdcache_revoking = ci->i_rdcache_gen; 1999 2011 } 2000 2012 tried_invalidate = true; 2001 - goto retry_locked; 2013 + goto retry; 2002 2014 } 2003 2015 2004 2016 for (p = rb_first(&ci->i_caps); p; p = rb_next(p)) { ··· 2011 2023 if (mds >= cap->mds || 2012 2024 ((flags & CHECK_CAPS_AUTHONLY) && cap != ci->i_auth_cap)) 2013 2025 continue; 2014 - 2015 - /* NOTE: no side-effects allowed, until we take s_mutex */ 2016 2026 2017 2027 /* 2018 2028 * If we have an auth cap, we don't need to consider any ··· 2074 2088 continue; /* nope, all good */ 2075 2089 2076 2090 ack: 2077 - if (session && session != cap->session) { 2078 - dout("oops, wrong session %p mutex\n", session); 2079 - mutex_unlock(&session->s_mutex); 2080 - session = NULL; 2081 - } 2082 - if (!session) { 2083 - session = cap->session; 2084 - if (mutex_trylock(&session->s_mutex) == 0) { 2085 - dout("inverting session/ino locks on %p\n", 2086 - session); 2087 - session = ceph_get_mds_session(session); 2088 - spin_unlock(&ci->i_ceph_lock); 2089 - if (took_snap_rwsem) { 2090 - up_read(&mdsc->snap_rwsem); 2091 - took_snap_rwsem = 0; 2092 - } 2093 - if (session) { 2094 - mutex_lock(&session->s_mutex); 2095 - ceph_put_mds_session(session); 2096 - } else { 2097 - /* 2098 - * Because we take the reference while 2099 - * holding the i_ceph_lock, it should 2100 - * never be NULL. Throw a warning if it 2101 - * ever is. 2102 - */ 2103 - WARN_ON_ONCE(true); 2104 - } 2105 - goto retry; 2106 - } 2107 - } 2091 + ceph_put_mds_session(session); 2092 + session = ceph_get_mds_session(cap->session); 2108 2093 2109 2094 /* kick flushing and flush snaps before sending normal 2110 2095 * cap message */ ··· 2087 2130 if (ci->i_ceph_flags & CEPH_I_FLUSH_SNAPS) 2088 2131 __ceph_flush_snaps(ci, session); 2089 2132 2090 - goto retry_locked; 2091 - } 2092 - 2093 - /* take snap_rwsem after session mutex */ 2094 - if (!took_snap_rwsem) { 2095 - if (down_read_trylock(&mdsc->snap_rwsem) == 0) { 2096 - dout("inverting snap/in locks on %p\n", 2097 - inode); 2098 - spin_unlock(&ci->i_ceph_lock); 2099 - down_read(&mdsc->snap_rwsem); 2100 - took_snap_rwsem = 1; 2101 - goto retry; 2102 - } 2103 - took_snap_rwsem = 1; 2133 + goto retry; 2104 2134 } 2105 2135 2106 2136 if (cap == ci->i_auth_cap && ci->i_dirty_caps) { ··· 2109 2165 2110 2166 __prep_cap(&arg, cap, CEPH_CAP_OP_UPDATE, mflags, cap_used, 2111 2167 want, retain, flushing, flush_tid, oldest_flush_tid); 2112 - spin_unlock(&ci->i_ceph_lock); 2113 2168 2169 + spin_unlock(&ci->i_ceph_lock); 2114 2170 __send_cap(&arg, ci); 2171 + spin_lock(&ci->i_ceph_lock); 2115 2172 2116 2173 goto retry; /* retake i_ceph_lock and restart our cap scan. */ 2117 2174 } ··· 2127 2182 2128 2183 spin_unlock(&ci->i_ceph_lock); 2129 2184 2185 + ceph_put_mds_session(session); 2130 2186 if (queue_invalidate) 2131 2187 ceph_queue_invalidate(inode); 2132 - 2133 - if (session) 2134 - mutex_unlock(&session->s_mutex); 2135 - if (took_snap_rwsem) 2136 - up_read(&mdsc->snap_rwsem); 2137 2188 } 2138 2189 2139 2190 /* ··· 2139 2198 { 2140 2199 struct ceph_mds_client *mdsc = ceph_sb_to_client(inode->i_sb)->mdsc; 2141 2200 struct ceph_inode_info *ci = ceph_inode(inode); 2142 - struct ceph_mds_session *session = NULL; 2143 2201 int flushing = 0; 2144 2202 u64 flush_tid = 0, oldest_flush_tid = 0; 2145 2203 2146 - retry: 2147 2204 spin_lock(&ci->i_ceph_lock); 2148 2205 retry_locked: 2149 2206 if (ci->i_dirty_caps && ci->i_auth_cap) { 2150 2207 struct ceph_cap *cap = ci->i_auth_cap; 2151 2208 struct cap_msg_args arg; 2209 + struct ceph_mds_session *session = cap->session; 2152 2210 2153 - if (session != cap->session) { 2154 - spin_unlock(&ci->i_ceph_lock); 2155 - if (session) 2156 - mutex_unlock(&session->s_mutex); 2157 - session = cap->session; 2158 - mutex_lock(&session->s_mutex); 2159 - goto retry; 2160 - } 2161 - if (cap->session->s_state < CEPH_MDS_SESSION_OPEN) { 2211 + if (session->s_state < CEPH_MDS_SESSION_OPEN) { 2162 2212 spin_unlock(&ci->i_ceph_lock); 2163 2213 goto out; 2164 2214 } ··· 2186 2254 spin_unlock(&ci->i_ceph_lock); 2187 2255 } 2188 2256 out: 2189 - if (session) 2190 - mutex_unlock(&session->s_mutex); 2191 - 2192 2257 *ptid = flush_tid; 2193 2258 return flushing; 2194 2259 } ··· 3142 3213 if (complete_capsnap) 3143 3214 wake_up_all(&ci->i_cap_wq); 3144 3215 while (put-- > 0) { 3145 - /* avoid calling iput_final() in osd dispatch threads */ 3146 - ceph_async_iput(inode); 3216 + iput(inode); 3147 3217 } 3148 3218 } 3149 3219 ··· 3216 3288 u64 size = le64_to_cpu(grant->size); 3217 3289 u64 max_size = le64_to_cpu(grant->max_size); 3218 3290 unsigned char check_caps = 0; 3219 - bool was_stale = cap->cap_gen < session->s_cap_gen; 3291 + bool was_stale = cap->cap_gen < atomic_read(&session->s_cap_gen); 3220 3292 bool wake = false; 3221 3293 bool writeback = false; 3222 3294 bool queue_trunc = false; ··· 3268 3340 } 3269 3341 3270 3342 /* side effects now are allowed */ 3271 - cap->cap_gen = session->s_cap_gen; 3343 + cap->cap_gen = atomic_read(&session->s_cap_gen); 3272 3344 cap->seq = seq; 3273 3345 3274 3346 __check_cap_issue(ci, cap, newcaps); ··· 3481 3553 if (wake) 3482 3554 wake_up_all(&ci->i_cap_wq); 3483 3555 3556 + mutex_unlock(&session->s_mutex); 3484 3557 if (check_caps == 1) 3485 3558 ceph_check_caps(ci, CHECK_CAPS_AUTHONLY | CHECK_CAPS_NOINVAL, 3486 3559 session); 3487 3560 else if (check_caps == 2) 3488 3561 ceph_check_caps(ci, CHECK_CAPS_NOINVAL, session); 3489 - else 3490 - mutex_unlock(&session->s_mutex); 3491 3562 } 3492 3563 3493 3564 /* ··· 4130 4203 mutex_unlock(&session->s_mutex); 4131 4204 done_unlocked: 4132 4205 ceph_put_string(extra_info.pool_ns); 4133 - /* avoid calling iput_final() in mds dispatch threads */ 4134 - ceph_async_iput(inode); 4206 + iput(inode); 4135 4207 return; 4136 4208 4137 4209 flush_cap_releases: ··· 4172 4246 spin_unlock(&mdsc->cap_delay_lock); 4173 4247 dout("check_delayed_caps on %p\n", inode); 4174 4248 ceph_check_caps(ci, 0, NULL); 4175 - /* avoid calling iput_final() in tick thread */ 4176 - ceph_async_iput(inode); 4249 + iput(inode); 4177 4250 spin_lock(&mdsc->cap_delay_lock); 4178 4251 } 4179 4252 }
+33 -4
fs/ceph/debugfs.c
··· 127 127 return 0; 128 128 } 129 129 130 - #define CEPH_METRIC_SHOW(name, total, avg, min, max, sq) { \ 130 + #define CEPH_LAT_METRIC_SHOW(name, total, avg, min, max, sq) { \ 131 131 s64 _total, _avg, _min, _max, _sq, _st; \ 132 132 _avg = ktime_to_us(avg); \ 133 133 _min = ktime_to_us(min == KTIME_MAX ? 0 : min); \ ··· 140 140 name, total, _avg, _min, _max, _st); \ 141 141 } 142 142 143 + #define CEPH_SZ_METRIC_SHOW(name, total, avg, min, max, sum) { \ 144 + u64 _min = min == U64_MAX ? 0 : min; \ 145 + seq_printf(s, "%-14s%-12lld%-16llu%-16llu%-16llu%llu\n", \ 146 + name, total, avg, _min, max, sum); \ 147 + } 148 + 143 149 static int metric_show(struct seq_file *s, void *p) 144 150 { 145 151 struct ceph_fs_client *fsc = s->private; ··· 153 147 struct ceph_client_metric *m = &mdsc->metric; 154 148 int nr_caps = 0; 155 149 s64 total, sum, avg, min, max, sq; 150 + u64 sum_sz, avg_sz, min_sz, max_sz; 156 151 157 152 sum = percpu_counter_sum(&m->total_inodes); 158 153 seq_printf(s, "item total\n"); ··· 177 170 max = m->read_latency_max; 178 171 sq = m->read_latency_sq_sum; 179 172 spin_unlock(&m->read_metric_lock); 180 - CEPH_METRIC_SHOW("read", total, avg, min, max, sq); 173 + CEPH_LAT_METRIC_SHOW("read", total, avg, min, max, sq); 181 174 182 175 spin_lock(&m->write_metric_lock); 183 176 total = m->total_writes; ··· 187 180 max = m->write_latency_max; 188 181 sq = m->write_latency_sq_sum; 189 182 spin_unlock(&m->write_metric_lock); 190 - CEPH_METRIC_SHOW("write", total, avg, min, max, sq); 183 + CEPH_LAT_METRIC_SHOW("write", total, avg, min, max, sq); 191 184 192 185 spin_lock(&m->metadata_metric_lock); 193 186 total = m->total_metadatas; ··· 197 190 max = m->metadata_latency_max; 198 191 sq = m->metadata_latency_sq_sum; 199 192 spin_unlock(&m->metadata_metric_lock); 200 - CEPH_METRIC_SHOW("metadata", total, avg, min, max, sq); 193 + CEPH_LAT_METRIC_SHOW("metadata", total, avg, min, max, sq); 194 + 195 + seq_printf(s, "\n"); 196 + seq_printf(s, "item total avg_sz(bytes) min_sz(bytes) max_sz(bytes) total_sz(bytes)\n"); 197 + seq_printf(s, "----------------------------------------------------------------------------------------\n"); 198 + 199 + spin_lock(&m->read_metric_lock); 200 + total = m->total_reads; 201 + sum_sz = m->read_size_sum; 202 + avg_sz = total > 0 ? DIV64_U64_ROUND_CLOSEST(sum_sz, total) : 0; 203 + min_sz = m->read_size_min; 204 + max_sz = m->read_size_max; 205 + spin_unlock(&m->read_metric_lock); 206 + CEPH_SZ_METRIC_SHOW("read", total, avg_sz, min_sz, max_sz, sum_sz); 207 + 208 + spin_lock(&m->write_metric_lock); 209 + total = m->total_writes; 210 + sum_sz = m->write_size_sum; 211 + avg_sz = total > 0 ? DIV64_U64_ROUND_CLOSEST(sum_sz, total) : 0; 212 + min_sz = m->write_size_min; 213 + max_sz = m->write_size_max; 214 + spin_unlock(&m->write_metric_lock); 215 + CEPH_SZ_METRIC_SHOW("write", total, avg_sz, min_sz, max_sz, sum_sz); 201 216 202 217 seq_printf(s, "\n"); 203 218 seq_printf(s, "item total miss hit\n");
+11 -5
fs/ceph/dir.c
··· 788 788 mask |= CEPH_CAP_XATTR_SHARED; 789 789 req->r_args.getattr.mask = cpu_to_le32(mask); 790 790 791 + ihold(dir); 791 792 req->r_parent = dir; 792 793 set_bit(CEPH_MDS_R_PARENT_LOCKED, &req->r_req_flags); 793 794 err = ceph_mdsc_do_request(mdsc, NULL, req); ··· 869 868 req->r_dentry = dget(dentry); 870 869 req->r_num_caps = 2; 871 870 req->r_parent = dir; 871 + ihold(dir); 872 872 set_bit(CEPH_MDS_R_PARENT_LOCKED, &req->r_req_flags); 873 873 req->r_args.mknod.mode = cpu_to_le32(mode); 874 874 req->r_args.mknod.rdev = cpu_to_le32(rdev); ··· 931 929 goto out; 932 930 } 933 931 req->r_parent = dir; 932 + ihold(dir); 933 + 934 934 set_bit(CEPH_MDS_R_PARENT_LOCKED, &req->r_req_flags); 935 935 req->r_dentry = dget(dentry); 936 936 req->r_num_caps = 2; ··· 997 993 req->r_dentry = dget(dentry); 998 994 req->r_num_caps = 2; 999 995 req->r_parent = dir; 996 + ihold(dir); 1000 997 set_bit(CEPH_MDS_R_PARENT_LOCKED, &req->r_req_flags); 1001 998 req->r_args.mkdir.mode = cpu_to_le32(mode); 1002 999 req->r_dentry_drop = CEPH_CAP_FILE_SHARED | CEPH_CAP_AUTH_EXCL; ··· 1042 1037 req->r_num_caps = 2; 1043 1038 req->r_old_dentry = dget(old_dentry); 1044 1039 req->r_parent = dir; 1040 + ihold(dir); 1045 1041 set_bit(CEPH_MDS_R_PARENT_LOCKED, &req->r_req_flags); 1046 1042 req->r_dentry_drop = CEPH_CAP_FILE_SHARED; 1047 1043 req->r_dentry_unless = CEPH_CAP_FILE_EXCL; ··· 1164 1158 req->r_dentry = dget(dentry); 1165 1159 req->r_num_caps = 2; 1166 1160 req->r_parent = dir; 1161 + ihold(dir); 1167 1162 req->r_dentry_drop = CEPH_CAP_FILE_SHARED; 1168 1163 req->r_dentry_unless = CEPH_CAP_FILE_EXCL; 1169 1164 req->r_inode_drop = ceph_drop_caps_for_unlink(inode); ··· 1239 1232 req->r_old_dentry = dget(old_dentry); 1240 1233 req->r_old_dentry_dir = old_dir; 1241 1234 req->r_parent = new_dir; 1235 + ihold(new_dir); 1242 1236 set_bit(CEPH_MDS_R_PARENT_LOCKED, &req->r_req_flags); 1243 1237 req->r_old_dentry_drop = CEPH_CAP_FILE_SHARED; 1244 1238 req->r_old_dentry_unless = CEPH_CAP_FILE_EXCL; ··· 1556 1548 u32 gen; 1557 1549 unsigned long ttl; 1558 1550 1559 - spin_lock(&session->s_gen_ttl_lock); 1560 - gen = session->s_cap_gen; 1551 + gen = atomic_read(&session->s_cap_gen); 1561 1552 ttl = session->s_cap_ttl; 1562 - spin_unlock(&session->s_gen_ttl_lock); 1563 1553 1564 1554 if (di->lease_gen == gen && 1565 1555 time_before(jiffies, ttl) && ··· 1736 1730 req->r_dentry = dget(dentry); 1737 1731 req->r_num_caps = 2; 1738 1732 req->r_parent = dir; 1733 + ihold(dir); 1739 1734 1740 1735 mask = CEPH_STAT_CAP_INODE | CEPH_CAP_AUTH_SHARED; 1741 1736 if (ceph_security_xattr_wanted(dir)) ··· 1816 1809 dentry->d_fsdata = NULL; 1817 1810 spin_unlock(&dentry->d_lock); 1818 1811 1819 - if (di->lease_session) 1820 - ceph_put_mds_session(di->lease_session); 1812 + ceph_put_mds_session(di->lease_session); 1821 1813 kmem_cache_free(ceph_dentry_cachep, di); 1822 1814 } 1823 1815
+1
fs/ceph/export.c
··· 542 542 ihold(inode); 543 543 req->r_ino2 = ceph_vino(d_inode(parent)); 544 544 req->r_parent = d_inode(parent); 545 + ihold(req->r_parent); 545 546 set_bit(CEPH_MDS_R_PARENT_LOCKED, &req->r_req_flags); 546 547 req->r_num_caps = 2; 547 548 err = ceph_mdsc_do_request(mdsc, NULL, req);
+12 -12
fs/ceph/file.c
··· 706 706 mask |= CEPH_CAP_XATTR_SHARED; 707 707 req->r_args.open.mask = cpu_to_le32(mask); 708 708 req->r_parent = dir; 709 + ihold(dir); 709 710 710 711 if (flags & O_CREAT) { 711 712 struct ceph_file_layout lo; ··· 904 903 ceph_update_read_metrics(&fsc->mdsc->metric, 905 904 req->r_start_latency, 906 905 req->r_end_latency, 907 - ret); 906 + len, ret); 908 907 909 908 ceph_osdc_put_request(req); 910 909 ··· 1036 1035 struct ceph_aio_request *aio_req = req->r_priv; 1037 1036 struct ceph_osd_data *osd_data = osd_req_op_extent_osd_data(req, 0); 1038 1037 struct ceph_client_metric *metric = &ceph_sb_to_mdsc(inode->i_sb)->metric; 1038 + unsigned int len = osd_data->bvec_pos.iter.bi_size; 1039 1039 1040 1040 BUG_ON(osd_data->type != CEPH_OSD_DATA_TYPE_BVECS); 1041 1041 BUG_ON(!osd_data->num_bvecs); 1042 1042 1043 - dout("ceph_aio_complete_req %p rc %d bytes %u\n", 1044 - inode, rc, osd_data->bvec_pos.iter.bi_size); 1043 + dout("ceph_aio_complete_req %p rc %d bytes %u\n", inode, rc, len); 1045 1044 1046 1045 if (rc == -EOLDSNAPC) { 1047 1046 struct ceph_aio_work *aio_work; ··· 1059 1058 } else if (!aio_req->write) { 1060 1059 if (rc == -ENOENT) 1061 1060 rc = 0; 1062 - if (rc >= 0 && osd_data->bvec_pos.iter.bi_size > rc) { 1061 + if (rc >= 0 && len > rc) { 1063 1062 struct iov_iter i; 1064 - int zlen = osd_data->bvec_pos.iter.bi_size - rc; 1063 + int zlen = len - rc; 1065 1064 1066 1065 /* 1067 1066 * If read is satisfied by single OSD request, ··· 1078 1077 } 1079 1078 1080 1079 iov_iter_bvec(&i, READ, osd_data->bvec_pos.bvecs, 1081 - osd_data->num_bvecs, 1082 - osd_data->bvec_pos.iter.bi_size); 1080 + osd_data->num_bvecs, len); 1083 1081 iov_iter_advance(&i, rc); 1084 1082 iov_iter_zero(zlen, &i); 1085 1083 } ··· 1088 1088 if (req->r_start_latency) { 1089 1089 if (aio_req->write) 1090 1090 ceph_update_write_metrics(metric, req->r_start_latency, 1091 - req->r_end_latency, rc); 1091 + req->r_end_latency, len, rc); 1092 1092 else 1093 1093 ceph_update_read_metrics(metric, req->r_start_latency, 1094 - req->r_end_latency, rc); 1094 + req->r_end_latency, len, rc); 1095 1095 } 1096 1096 1097 1097 put_bvecs(osd_data->bvec_pos.bvecs, osd_data->num_bvecs, ··· 1299 1299 1300 1300 if (write) 1301 1301 ceph_update_write_metrics(metric, req->r_start_latency, 1302 - req->r_end_latency, ret); 1302 + req->r_end_latency, len, ret); 1303 1303 else 1304 1304 ceph_update_read_metrics(metric, req->r_start_latency, 1305 - req->r_end_latency, ret); 1305 + req->r_end_latency, len, ret); 1306 1306 1307 1307 size = i_size_read(inode); 1308 1308 if (!write) { ··· 1476 1476 ret = ceph_osdc_wait_request(&fsc->client->osdc, req); 1477 1477 1478 1478 ceph_update_write_metrics(&fsc->mdsc->metric, req->r_start_latency, 1479 - req->r_end_latency, ret); 1479 + req->r_end_latency, len, ret); 1480 1480 out: 1481 1481 ceph_osdc_put_request(req); 1482 1482 if (ret != 0) {
+7 -31
fs/ceph/inode.c
··· 1124 1124 return; 1125 1125 } 1126 1126 1127 - if (di->lease_gen == session->s_cap_gen && 1127 + if (di->lease_gen == atomic_read(&session->s_cap_gen) && 1128 1128 time_before(ttl, di->time)) 1129 1129 return; /* we already have a newer lease. */ 1130 1130 ··· 1135 1135 1136 1136 if (!di->lease_session) 1137 1137 di->lease_session = ceph_get_mds_session(session); 1138 - di->lease_gen = session->s_cap_gen; 1138 + di->lease_gen = atomic_read(&session->s_cap_gen); 1139 1139 di->lease_seq = le32_to_cpu(lease->seq); 1140 1140 di->lease_renew_after = half_ttl; 1141 1141 di->lease_renew_from = 0; ··· 1154 1154 __update_dentry_lease(dir, dentry, lease, session, from_time, 1155 1155 &old_lease_session); 1156 1156 spin_unlock(&dentry->d_lock); 1157 - if (old_lease_session) 1158 - ceph_put_mds_session(old_lease_session); 1157 + ceph_put_mds_session(old_lease_session); 1159 1158 } 1160 1159 1161 1160 /* ··· 1199 1200 from_time, &old_lease_session); 1200 1201 out_unlock: 1201 1202 spin_unlock(&dentry->d_lock); 1202 - if (old_lease_session) 1203 - ceph_put_mds_session(old_lease_session); 1203 + ceph_put_mds_session(old_lease_session); 1204 1204 } 1205 1205 1206 1206 /* ··· 1566 1568 unlock_new_inode(in); 1567 1569 } 1568 1570 1569 - /* avoid calling iput_final() in mds dispatch threads */ 1570 - ceph_async_iput(in); 1571 + iput(in); 1571 1572 } 1572 1573 1573 1574 return err; ··· 1763 1766 if (ret < 0) { 1764 1767 pr_err("ceph_fill_inode badness on %p\n", in); 1765 1768 if (d_really_is_negative(dn)) { 1766 - /* avoid calling iput_final() in mds 1767 - * dispatch threads */ 1768 1769 if (in->i_state & I_NEW) { 1769 1770 ihold(in); 1770 1771 discard_new_inode(in); 1771 1772 } 1772 - ceph_async_iput(in); 1773 + iput(in); 1773 1774 } 1774 1775 d_drop(dn); 1775 1776 err = ret; ··· 1780 1785 if (ceph_security_xattr_deadlock(in)) { 1781 1786 dout(" skip splicing dn %p to inode %p" 1782 1787 " (security xattr deadlock)\n", dn, in); 1783 - ceph_async_iput(in); 1788 + iput(in); 1784 1789 skipped++; 1785 1790 goto next_item; 1786 1791 } ··· 1829 1834 1830 1835 spin_unlock(&ci->i_ceph_lock); 1831 1836 return ret; 1832 - } 1833 - 1834 - /* 1835 - * Put reference to inode, but avoid calling iput_final() in current thread. 1836 - * iput_final() may wait for reahahead pages. The wait can cause deadlock in 1837 - * some contexts. 1838 - */ 1839 - void ceph_async_iput(struct inode *inode) 1840 - { 1841 - if (!inode) 1842 - return; 1843 - for (;;) { 1844 - if (atomic_add_unless(&inode->i_count, -1, 1)) 1845 - break; 1846 - if (queue_work(ceph_inode_to_client(inode)->inode_wq, 1847 - &ceph_inode(inode)->i_work)) 1848 - break; 1849 - /* queue work failed, i_count must be at least 2 */ 1850 - } 1851 1837 } 1852 1838 1853 1839 void ceph_queue_inode_work(struct inode *inode, int work_bit)
+21 -33
fs/ceph/mds_client.c
··· 664 664 665 665 void ceph_put_mds_session(struct ceph_mds_session *s) 666 666 { 667 + if (IS_ERR_OR_NULL(s)) 668 + return; 669 + 667 670 dout("mdsc put_session %p %d -> %d\n", s, 668 671 refcount_read(&s->s_ref), refcount_read(&s->s_ref)-1); 669 672 if (refcount_dec_and_test(&s->s_ref)) { ··· 749 746 750 747 ceph_con_init(&s->s_con, s, &mds_con_ops, &mdsc->fsc->client->msgr); 751 748 752 - spin_lock_init(&s->s_gen_ttl_lock); 753 - s->s_cap_gen = 1; 749 + atomic_set(&s->s_cap_gen, 1); 754 750 s->s_cap_ttl = jiffies - 1; 755 751 756 752 spin_lock_init(&s->s_cap_lock); ··· 824 822 ceph_msg_put(req->r_reply); 825 823 if (req->r_inode) { 826 824 ceph_put_cap_refs(ceph_inode(req->r_inode), CEPH_CAP_PIN); 827 - /* avoid calling iput_final() in mds dispatch threads */ 828 - ceph_async_iput(req->r_inode); 825 + iput(req->r_inode); 829 826 } 830 827 if (req->r_parent) { 831 828 ceph_put_cap_refs(ceph_inode(req->r_parent), CEPH_CAP_PIN); 832 - ceph_async_iput(req->r_parent); 829 + iput(req->r_parent); 833 830 } 834 - ceph_async_iput(req->r_target_inode); 831 + iput(req->r_target_inode); 835 832 if (req->r_dentry) 836 833 dput(req->r_dentry); 837 834 if (req->r_old_dentry) ··· 844 843 */ 845 844 ceph_put_cap_refs(ceph_inode(req->r_old_dentry_dir), 846 845 CEPH_CAP_PIN); 847 - ceph_async_iput(req->r_old_dentry_dir); 846 + iput(req->r_old_dentry_dir); 848 847 } 849 848 kfree(req->r_path1); 850 849 kfree(req->r_path2); ··· 959 958 } 960 959 961 960 if (req->r_unsafe_dir) { 962 - /* avoid calling iput_final() in mds dispatch threads */ 963 - ceph_async_iput(req->r_unsafe_dir); 961 + iput(req->r_unsafe_dir); 964 962 req->r_unsafe_dir = NULL; 965 963 } 966 964 ··· 1130 1130 cap = rb_entry(rb_first(&ci->i_caps), struct ceph_cap, ci_node); 1131 1131 if (!cap) { 1132 1132 spin_unlock(&ci->i_ceph_lock); 1133 - ceph_async_iput(inode); 1133 + iput(inode); 1134 1134 goto random; 1135 1135 } 1136 1136 mds = cap->session->s_mds; ··· 1139 1139 cap == ci->i_auth_cap ? "auth " : "", cap); 1140 1140 spin_unlock(&ci->i_ceph_lock); 1141 1141 out: 1142 - /* avoid calling iput_final() while holding mdsc->mutex or 1143 - * in mds dispatch threads */ 1144 - ceph_async_iput(inode); 1142 + iput(inode); 1145 1143 return mds; 1146 1144 1147 1145 random: ··· 1436 1438 1437 1439 for (i = 0; i < mi->num_export_targets; i++) { 1438 1440 ts = __open_export_target_session(mdsc, mi->export_targets[i]); 1439 - if (!IS_ERR(ts)) 1440 - ceph_put_mds_session(ts); 1441 + ceph_put_mds_session(ts); 1441 1442 } 1442 1443 } 1443 1444 ··· 1542 1545 spin_unlock(&session->s_cap_lock); 1543 1546 1544 1547 if (last_inode) { 1545 - /* avoid calling iput_final() while holding 1546 - * s_mutex or in mds dispatch threads */ 1547 - ceph_async_iput(last_inode); 1548 + iput(last_inode); 1548 1549 last_inode = NULL; 1549 1550 } 1550 1551 if (old_cap) { ··· 1576 1581 session->s_cap_iterator = NULL; 1577 1582 spin_unlock(&session->s_cap_lock); 1578 1583 1579 - ceph_async_iput(last_inode); 1584 + iput(last_inode); 1580 1585 if (old_cap) 1581 1586 ceph_put_cap(session->s_mdsc, old_cap); 1582 1587 ··· 1716 1721 spin_unlock(&session->s_cap_lock); 1717 1722 1718 1723 inode = ceph_find_inode(sb, vino); 1719 - /* avoid calling iput_final() while holding s_mutex */ 1720 - ceph_async_iput(inode); 1724 + iput(inode); 1721 1725 1722 1726 spin_lock(&session->s_cap_lock); 1723 1727 } ··· 1755 1761 ci->i_requested_max_size = 0; 1756 1762 spin_unlock(&ci->i_ceph_lock); 1757 1763 } else if (ev == RENEWCAPS) { 1758 - if (cap->cap_gen < cap->session->s_cap_gen) { 1764 + if (cap->cap_gen < atomic_read(&cap->session->s_cap_gen)) { 1759 1765 /* mds did not re-issue stale cap */ 1760 1766 spin_lock(&ci->i_ceph_lock); 1761 1767 cap->issued = cap->implemented = CEPH_CAP_PIN; ··· 2982 2988 ceph_take_cap_refs(ci, CEPH_CAP_PIN, false); 2983 2989 __ceph_touch_fmode(ci, mdsc, fmode); 2984 2990 spin_unlock(&ci->i_ceph_lock); 2985 - ihold(req->r_parent); 2986 2991 } 2987 2992 if (req->r_old_dentry_dir) 2988 2993 ceph_get_cap_refs(ceph_inode(req->r_old_dentry_dir), ··· 3492 3499 case CEPH_SESSION_STALE: 3493 3500 pr_info("mds%d caps went stale, renewing\n", 3494 3501 session->s_mds); 3495 - spin_lock(&session->s_gen_ttl_lock); 3496 - session->s_cap_gen++; 3502 + atomic_inc(&session->s_cap_gen); 3497 3503 session->s_cap_ttl = jiffies - 1; 3498 - spin_unlock(&session->s_gen_ttl_lock); 3499 3504 send_renew_caps(mdsc, session); 3500 3505 break; 3501 3506 ··· 3762 3771 cap->seq = 0; /* reset cap seq */ 3763 3772 cap->issue_seq = 0; /* and issue_seq */ 3764 3773 cap->mseq = 0; /* and migrate_seq */ 3765 - cap->cap_gen = cap->session->s_cap_gen; 3774 + cap->cap_gen = atomic_read(&cap->session->s_cap_gen); 3766 3775 3767 3776 /* These are lost when the session goes away */ 3768 3777 if (S_ISDIR(inode->i_mode)) { ··· 4002 4011 dout("session %p state %s\n", session, 4003 4012 ceph_session_state_name(session->s_state)); 4004 4013 4005 - spin_lock(&session->s_gen_ttl_lock); 4006 - session->s_cap_gen++; 4007 - spin_unlock(&session->s_gen_ttl_lock); 4014 + atomic_inc(&session->s_cap_gen); 4008 4015 4009 4016 spin_lock(&session->s_cap_lock); 4010 4017 /* don't know if session is readonly */ ··· 4333 4344 4334 4345 case CEPH_MDS_LEASE_RENEW: 4335 4346 if (di->lease_session == session && 4336 - di->lease_gen == session->s_cap_gen && 4347 + di->lease_gen == atomic_read(&session->s_cap_gen) && 4337 4348 di->lease_renew_from && 4338 4349 di->lease_renew_after == 0) { 4339 4350 unsigned long duration = ··· 4361 4372 4362 4373 out: 4363 4374 mutex_unlock(&session->s_mutex); 4364 - /* avoid calling iput_final() in mds dispatch threads */ 4365 - ceph_async_iput(inode); 4375 + iput(inode); 4366 4376 return; 4367 4377 4368 4378 bad:
+2 -4
fs/ceph/mds_client.h
··· 186 186 187 187 struct ceph_auth_handshake s_auth; 188 188 189 - /* protected by s_gen_ttl_lock */ 190 - spinlock_t s_gen_ttl_lock; 191 - u32 s_cap_gen; /* inc each time we get mds stale msg */ 192 - unsigned long s_cap_ttl; /* when session caps expire */ 189 + atomic_t s_cap_gen; /* inc each time we get mds stale msg */ 190 + unsigned long s_cap_ttl; /* when session caps expire. protected by s_mutex */ 193 191 194 192 /* protected by s_cap_lock */ 195 193 spinlock_t s_cap_lock;
+109 -58
fs/ceph/metric.c
··· 20 20 struct ceph_opened_files *files; 21 21 struct ceph_pinned_icaps *icaps; 22 22 struct ceph_opened_inodes *inodes; 23 + struct ceph_read_io_size *rsize; 24 + struct ceph_write_io_size *wsize; 23 25 struct ceph_client_metric *m = &mdsc->metric; 24 26 u64 nr_caps = atomic64_read(&m->total_caps); 27 + u32 header_len = sizeof(struct ceph_metric_header); 25 28 struct ceph_msg *msg; 26 29 struct timespec64 ts; 27 30 s64 sum; ··· 33 30 34 31 len = sizeof(*head) + sizeof(*cap) + sizeof(*read) + sizeof(*write) 35 32 + sizeof(*meta) + sizeof(*dlease) + sizeof(*files) 36 - + sizeof(*icaps) + sizeof(*inodes); 33 + + sizeof(*icaps) + sizeof(*inodes) + sizeof(*rsize) 34 + + sizeof(*wsize); 37 35 38 36 msg = ceph_msg_new(CEPH_MSG_CLIENT_METRICS, len, GFP_NOFS, true); 39 37 if (!msg) { ··· 47 43 48 44 /* encode the cap metric */ 49 45 cap = (struct ceph_metric_cap *)(head + 1); 50 - cap->type = cpu_to_le32(CLIENT_METRIC_TYPE_CAP_INFO); 51 - cap->ver = 1; 52 - cap->compat = 1; 53 - cap->data_len = cpu_to_le32(sizeof(*cap) - 10); 46 + cap->header.type = cpu_to_le32(CLIENT_METRIC_TYPE_CAP_INFO); 47 + cap->header.ver = 1; 48 + cap->header.compat = 1; 49 + cap->header.data_len = cpu_to_le32(sizeof(*cap) - header_len); 54 50 cap->hit = cpu_to_le64(percpu_counter_sum(&m->i_caps_hit)); 55 51 cap->mis = cpu_to_le64(percpu_counter_sum(&m->i_caps_mis)); 56 52 cap->total = cpu_to_le64(nr_caps); ··· 58 54 59 55 /* encode the read latency metric */ 60 56 read = (struct ceph_metric_read_latency *)(cap + 1); 61 - read->type = cpu_to_le32(CLIENT_METRIC_TYPE_READ_LATENCY); 62 - read->ver = 1; 63 - read->compat = 1; 64 - read->data_len = cpu_to_le32(sizeof(*read) - 10); 57 + read->header.type = cpu_to_le32(CLIENT_METRIC_TYPE_READ_LATENCY); 58 + read->header.ver = 1; 59 + read->header.compat = 1; 60 + read->header.data_len = cpu_to_le32(sizeof(*read) - header_len); 65 61 sum = m->read_latency_sum; 66 62 jiffies_to_timespec64(sum, &ts); 67 63 read->sec = cpu_to_le32(ts.tv_sec); ··· 70 66 71 67 /* encode the write latency metric */ 72 68 write = (struct ceph_metric_write_latency *)(read + 1); 73 - write->type = cpu_to_le32(CLIENT_METRIC_TYPE_WRITE_LATENCY); 74 - write->ver = 1; 75 - write->compat = 1; 76 - write->data_len = cpu_to_le32(sizeof(*write) - 10); 69 + write->header.type = cpu_to_le32(CLIENT_METRIC_TYPE_WRITE_LATENCY); 70 + write->header.ver = 1; 71 + write->header.compat = 1; 72 + write->header.data_len = cpu_to_le32(sizeof(*write) - header_len); 77 73 sum = m->write_latency_sum; 78 74 jiffies_to_timespec64(sum, &ts); 79 75 write->sec = cpu_to_le32(ts.tv_sec); ··· 82 78 83 79 /* encode the metadata latency metric */ 84 80 meta = (struct ceph_metric_metadata_latency *)(write + 1); 85 - meta->type = cpu_to_le32(CLIENT_METRIC_TYPE_METADATA_LATENCY); 86 - meta->ver = 1; 87 - meta->compat = 1; 88 - meta->data_len = cpu_to_le32(sizeof(*meta) - 10); 81 + meta->header.type = cpu_to_le32(CLIENT_METRIC_TYPE_METADATA_LATENCY); 82 + meta->header.ver = 1; 83 + meta->header.compat = 1; 84 + meta->header.data_len = cpu_to_le32(sizeof(*meta) - header_len); 89 85 sum = m->metadata_latency_sum; 90 86 jiffies_to_timespec64(sum, &ts); 91 87 meta->sec = cpu_to_le32(ts.tv_sec); ··· 94 90 95 91 /* encode the dentry lease metric */ 96 92 dlease = (struct ceph_metric_dlease *)(meta + 1); 97 - dlease->type = cpu_to_le32(CLIENT_METRIC_TYPE_DENTRY_LEASE); 98 - dlease->ver = 1; 99 - dlease->compat = 1; 100 - dlease->data_len = cpu_to_le32(sizeof(*dlease) - 10); 93 + dlease->header.type = cpu_to_le32(CLIENT_METRIC_TYPE_DENTRY_LEASE); 94 + dlease->header.ver = 1; 95 + dlease->header.compat = 1; 96 + dlease->header.data_len = cpu_to_le32(sizeof(*dlease) - header_len); 101 97 dlease->hit = cpu_to_le64(percpu_counter_sum(&m->d_lease_hit)); 102 98 dlease->mis = cpu_to_le64(percpu_counter_sum(&m->d_lease_mis)); 103 99 dlease->total = cpu_to_le64(atomic64_read(&m->total_dentries)); ··· 107 103 108 104 /* encode the opened files metric */ 109 105 files = (struct ceph_opened_files *)(dlease + 1); 110 - files->type = cpu_to_le32(CLIENT_METRIC_TYPE_OPENED_FILES); 111 - files->ver = 1; 112 - files->compat = 1; 113 - files->data_len = cpu_to_le32(sizeof(*files) - 10); 106 + files->header.type = cpu_to_le32(CLIENT_METRIC_TYPE_OPENED_FILES); 107 + files->header.ver = 1; 108 + files->header.compat = 1; 109 + files->header.data_len = cpu_to_le32(sizeof(*files) - header_len); 114 110 files->opened_files = cpu_to_le64(atomic64_read(&m->opened_files)); 115 111 files->total = cpu_to_le64(sum); 116 112 items++; 117 113 118 114 /* encode the pinned icaps metric */ 119 115 icaps = (struct ceph_pinned_icaps *)(files + 1); 120 - icaps->type = cpu_to_le32(CLIENT_METRIC_TYPE_PINNED_ICAPS); 121 - icaps->ver = 1; 122 - icaps->compat = 1; 123 - icaps->data_len = cpu_to_le32(sizeof(*icaps) - 10); 116 + icaps->header.type = cpu_to_le32(CLIENT_METRIC_TYPE_PINNED_ICAPS); 117 + icaps->header.ver = 1; 118 + icaps->header.compat = 1; 119 + icaps->header.data_len = cpu_to_le32(sizeof(*icaps) - header_len); 124 120 icaps->pinned_icaps = cpu_to_le64(nr_caps); 125 121 icaps->total = cpu_to_le64(sum); 126 122 items++; 127 123 128 124 /* encode the opened inodes metric */ 129 125 inodes = (struct ceph_opened_inodes *)(icaps + 1); 130 - inodes->type = cpu_to_le32(CLIENT_METRIC_TYPE_OPENED_INODES); 131 - inodes->ver = 1; 132 - inodes->compat = 1; 133 - inodes->data_len = cpu_to_le32(sizeof(*inodes) - 10); 126 + inodes->header.type = cpu_to_le32(CLIENT_METRIC_TYPE_OPENED_INODES); 127 + inodes->header.ver = 1; 128 + inodes->header.compat = 1; 129 + inodes->header.data_len = cpu_to_le32(sizeof(*inodes) - header_len); 134 130 inodes->opened_inodes = cpu_to_le64(percpu_counter_sum(&m->opened_inodes)); 135 131 inodes->total = cpu_to_le64(sum); 132 + items++; 133 + 134 + /* encode the read io size metric */ 135 + rsize = (struct ceph_read_io_size *)(inodes + 1); 136 + rsize->header.type = cpu_to_le32(CLIENT_METRIC_TYPE_READ_IO_SIZES); 137 + rsize->header.ver = 1; 138 + rsize->header.compat = 1; 139 + rsize->header.data_len = cpu_to_le32(sizeof(*rsize) - header_len); 140 + rsize->total_ops = cpu_to_le64(m->total_reads); 141 + rsize->total_size = cpu_to_le64(m->read_size_sum); 142 + items++; 143 + 144 + /* encode the write io size metric */ 145 + wsize = (struct ceph_write_io_size *)(rsize + 1); 146 + wsize->header.type = cpu_to_le32(CLIENT_METRIC_TYPE_WRITE_IO_SIZES); 147 + wsize->header.ver = 1; 148 + wsize->header.compat = 1; 149 + wsize->header.data_len = cpu_to_le32(sizeof(*wsize) - header_len); 150 + wsize->total_ops = cpu_to_le64(m->total_writes); 151 + wsize->total_size = cpu_to_le64(m->write_size_sum); 136 152 items++; 137 153 138 154 put_unaligned_le32(items, &head->num); ··· 249 225 m->read_latency_max = 0; 250 226 m->total_reads = 0; 251 227 m->read_latency_sum = 0; 228 + m->read_size_min = U64_MAX; 229 + m->read_size_max = 0; 230 + m->read_size_sum = 0; 252 231 253 232 spin_lock_init(&m->write_metric_lock); 254 233 m->write_latency_sq_sum = 0; ··· 259 232 m->write_latency_max = 0; 260 233 m->total_writes = 0; 261 234 m->write_latency_sum = 0; 235 + m->write_size_min = U64_MAX; 236 + m->write_size_max = 0; 237 + m->write_size_sum = 0; 262 238 263 239 spin_lock_init(&m->metadata_metric_lock); 264 240 m->metadata_latency_sq_sum = 0; ··· 311 281 312 282 cancel_delayed_work_sync(&m->delayed_work); 313 283 314 - if (m->session) 315 - ceph_put_mds_session(m->session); 284 + ceph_put_mds_session(m->session); 316 285 } 317 286 318 - static inline void __update_latency(ktime_t *totalp, ktime_t *lsump, 319 - ktime_t *min, ktime_t *max, 320 - ktime_t *sq_sump, ktime_t lat) 287 + #define METRIC_UPDATE_MIN_MAX(min, max, new) \ 288 + { \ 289 + if (unlikely(new < min)) \ 290 + min = new; \ 291 + if (unlikely(new > max)) \ 292 + max = new; \ 293 + } 294 + 295 + static inline void __update_stdev(ktime_t total, ktime_t lsum, 296 + ktime_t *sq_sump, ktime_t lat) 321 297 { 322 - ktime_t total, avg, sq, lsum; 323 - 324 - total = ++(*totalp); 325 - lsum = (*lsump += lat); 326 - 327 - if (unlikely(lat < *min)) 328 - *min = lat; 329 - if (unlikely(lat > *max)) 330 - *max = lat; 298 + ktime_t avg, sq; 331 299 332 300 if (unlikely(total == 1)) 333 301 return; ··· 340 312 341 313 void ceph_update_read_metrics(struct ceph_client_metric *m, 342 314 ktime_t r_start, ktime_t r_end, 343 - int rc) 315 + unsigned int size, int rc) 344 316 { 345 317 ktime_t lat = ktime_sub(r_end, r_start); 318 + ktime_t total; 346 319 347 320 if (unlikely(rc < 0 && rc != -ENOENT && rc != -ETIMEDOUT)) 348 321 return; 349 322 350 323 spin_lock(&m->read_metric_lock); 351 - __update_latency(&m->total_reads, &m->read_latency_sum, 352 - &m->read_latency_min, &m->read_latency_max, 353 - &m->read_latency_sq_sum, lat); 324 + total = ++m->total_reads; 325 + m->read_size_sum += size; 326 + m->read_latency_sum += lat; 327 + METRIC_UPDATE_MIN_MAX(m->read_size_min, 328 + m->read_size_max, 329 + size); 330 + METRIC_UPDATE_MIN_MAX(m->read_latency_min, 331 + m->read_latency_max, 332 + lat); 333 + __update_stdev(total, m->read_latency_sum, 334 + &m->read_latency_sq_sum, lat); 354 335 spin_unlock(&m->read_metric_lock); 355 336 } 356 337 357 338 void ceph_update_write_metrics(struct ceph_client_metric *m, 358 339 ktime_t r_start, ktime_t r_end, 359 - int rc) 340 + unsigned int size, int rc) 360 341 { 361 342 ktime_t lat = ktime_sub(r_end, r_start); 343 + ktime_t total; 362 344 363 345 if (unlikely(rc && rc != -ETIMEDOUT)) 364 346 return; 365 347 366 348 spin_lock(&m->write_metric_lock); 367 - __update_latency(&m->total_writes, &m->write_latency_sum, 368 - &m->write_latency_min, &m->write_latency_max, 369 - &m->write_latency_sq_sum, lat); 349 + total = ++m->total_writes; 350 + m->write_size_sum += size; 351 + m->write_latency_sum += lat; 352 + METRIC_UPDATE_MIN_MAX(m->write_size_min, 353 + m->write_size_max, 354 + size); 355 + METRIC_UPDATE_MIN_MAX(m->write_latency_min, 356 + m->write_latency_max, 357 + lat); 358 + __update_stdev(total, m->write_latency_sum, 359 + &m->write_latency_sq_sum, lat); 370 360 spin_unlock(&m->write_metric_lock); 371 361 } 372 362 ··· 393 347 int rc) 394 348 { 395 349 ktime_t lat = ktime_sub(r_end, r_start); 350 + ktime_t total; 396 351 397 352 if (unlikely(rc && rc != -ENOENT)) 398 353 return; 399 354 400 355 spin_lock(&m->metadata_metric_lock); 401 - __update_latency(&m->total_metadatas, &m->metadata_latency_sum, 402 - &m->metadata_latency_min, &m->metadata_latency_max, 403 - &m->metadata_latency_sq_sum, lat); 356 + total = ++m->total_metadatas; 357 + m->metadata_latency_sum += lat; 358 + METRIC_UPDATE_MIN_MAX(m->metadata_latency_min, 359 + m->metadata_latency_max, 360 + lat); 361 + __update_stdev(total, m->metadata_latency_sum, 362 + &m->metadata_latency_sq_sum, lat); 404 363 spin_unlock(&m->metadata_metric_lock); 405 364 }
+40 -49
fs/ceph/metric.h
··· 17 17 CLIENT_METRIC_TYPE_OPENED_FILES, 18 18 CLIENT_METRIC_TYPE_PINNED_ICAPS, 19 19 CLIENT_METRIC_TYPE_OPENED_INODES, 20 + CLIENT_METRIC_TYPE_READ_IO_SIZES, 21 + CLIENT_METRIC_TYPE_WRITE_IO_SIZES, 20 22 21 - CLIENT_METRIC_TYPE_MAX = CLIENT_METRIC_TYPE_OPENED_INODES, 23 + CLIENT_METRIC_TYPE_MAX = CLIENT_METRIC_TYPE_WRITE_IO_SIZES, 22 24 }; 23 25 24 26 /* ··· 36 34 CLIENT_METRIC_TYPE_OPENED_FILES, \ 37 35 CLIENT_METRIC_TYPE_PINNED_ICAPS, \ 38 36 CLIENT_METRIC_TYPE_OPENED_INODES, \ 37 + CLIENT_METRIC_TYPE_READ_IO_SIZES, \ 38 + CLIENT_METRIC_TYPE_WRITE_IO_SIZES, \ 39 39 \ 40 40 CLIENT_METRIC_TYPE_MAX, \ 41 41 } 42 42 43 - /* metric caps header */ 44 - struct ceph_metric_cap { 43 + struct ceph_metric_header { 45 44 __le32 type; /* ceph metric type */ 46 - 47 45 __u8 ver; 48 46 __u8 compat; 49 - 50 47 __le32 data_len; /* length of sizeof(hit + mis + total) */ 48 + } __packed; 49 + 50 + /* metric caps header */ 51 + struct ceph_metric_cap { 52 + struct ceph_metric_header header; 51 53 __le64 hit; 52 54 __le64 mis; 53 55 __le64 total; ··· 59 53 60 54 /* metric read latency header */ 61 55 struct ceph_metric_read_latency { 62 - __le32 type; /* ceph metric type */ 63 - 64 - __u8 ver; 65 - __u8 compat; 66 - 67 - __le32 data_len; /* length of sizeof(sec + nsec) */ 56 + struct ceph_metric_header header; 68 57 __le32 sec; 69 58 __le32 nsec; 70 59 } __packed; 71 60 72 61 /* metric write latency header */ 73 62 struct ceph_metric_write_latency { 74 - __le32 type; /* ceph metric type */ 75 - 76 - __u8 ver; 77 - __u8 compat; 78 - 79 - __le32 data_len; /* length of sizeof(sec + nsec) */ 63 + struct ceph_metric_header header; 80 64 __le32 sec; 81 65 __le32 nsec; 82 66 } __packed; 83 67 84 68 /* metric metadata latency header */ 85 69 struct ceph_metric_metadata_latency { 86 - __le32 type; /* ceph metric type */ 87 - 88 - __u8 ver; 89 - __u8 compat; 90 - 91 - __le32 data_len; /* length of sizeof(sec + nsec) */ 70 + struct ceph_metric_header header; 92 71 __le32 sec; 93 72 __le32 nsec; 94 73 } __packed; 95 74 96 75 /* metric dentry lease header */ 97 76 struct ceph_metric_dlease { 98 - __le32 type; /* ceph metric type */ 99 - 100 - __u8 ver; 101 - __u8 compat; 102 - 103 - __le32 data_len; /* length of sizeof(hit + mis + total) */ 77 + struct ceph_metric_header header; 104 78 __le64 hit; 105 79 __le64 mis; 106 80 __le64 total; ··· 88 102 89 103 /* metric opened files header */ 90 104 struct ceph_opened_files { 91 - __le32 type; /* ceph metric type */ 92 - 93 - __u8 ver; 94 - __u8 compat; 95 - 96 - __le32 data_len; /* length of sizeof(opened_files + total) */ 105 + struct ceph_metric_header header; 97 106 __le64 opened_files; 98 107 __le64 total; 99 108 } __packed; 100 109 101 110 /* metric pinned i_caps header */ 102 111 struct ceph_pinned_icaps { 103 - __le32 type; /* ceph metric type */ 104 - 105 - __u8 ver; 106 - __u8 compat; 107 - 108 - __le32 data_len; /* length of sizeof(pinned_icaps + total) */ 112 + struct ceph_metric_header header; 109 113 __le64 pinned_icaps; 110 114 __le64 total; 111 115 } __packed; 112 116 113 117 /* metric opened inodes header */ 114 118 struct ceph_opened_inodes { 115 - __le32 type; /* ceph metric type */ 116 - 117 - __u8 ver; 118 - __u8 compat; 119 - 120 - __le32 data_len; /* length of sizeof(opened_inodes + total) */ 119 + struct ceph_metric_header header; 121 120 __le64 opened_inodes; 122 121 __le64 total; 122 + } __packed; 123 + 124 + /* metric read io size header */ 125 + struct ceph_read_io_size { 126 + struct ceph_metric_header header; 127 + __le64 total_ops; 128 + __le64 total_size; 129 + } __packed; 130 + 131 + /* metric write io size header */ 132 + struct ceph_write_io_size { 133 + struct ceph_metric_header header; 134 + __le64 total_ops; 135 + __le64 total_size; 123 136 } __packed; 124 137 125 138 struct ceph_metric_head { ··· 137 152 138 153 spinlock_t read_metric_lock; 139 154 u64 total_reads; 155 + u64 read_size_sum; 156 + u64 read_size_min; 157 + u64 read_size_max; 140 158 ktime_t read_latency_sum; 141 159 ktime_t read_latency_sq_sum; 142 160 ktime_t read_latency_min; ··· 147 159 148 160 spinlock_t write_metric_lock; 149 161 u64 total_writes; 162 + u64 write_size_sum; 163 + u64 write_size_min; 164 + u64 write_size_max; 150 165 ktime_t write_latency_sum; 151 166 ktime_t write_latency_sq_sum; 152 167 ktime_t write_latency_min; ··· 197 206 198 207 extern void ceph_update_read_metrics(struct ceph_client_metric *m, 199 208 ktime_t r_start, ktime_t r_end, 200 - int rc); 209 + unsigned int size, int rc); 201 210 extern void ceph_update_write_metrics(struct ceph_client_metric *m, 202 211 ktime_t r_start, ktime_t r_end, 203 - int rc); 212 + unsigned int size, int rc); 204 213 extern void ceph_update_metadata_metrics(struct ceph_client_metric *m, 205 214 ktime_t r_start, ktime_t r_end, 206 215 int rc);
+3 -6
fs/ceph/quota.c
··· 74 74 le64_to_cpu(h->max_files)); 75 75 spin_unlock(&ci->i_ceph_lock); 76 76 77 - /* avoid calling iput_final() in dispatch thread */ 78 - ceph_async_iput(inode); 77 + iput(inode); 79 78 } 80 79 81 80 static struct ceph_quotarealm_inode * ··· 246 247 247 248 ci = ceph_inode(in); 248 249 has_quota = __ceph_has_any_quota(ci); 249 - /* avoid calling iput_final() while holding mdsc->snap_rwsem */ 250 - ceph_async_iput(in); 250 + iput(in); 251 251 252 252 next = realm->parent; 253 253 if (has_quota || !next) ··· 381 383 pr_warn("Invalid quota check op (%d)\n", op); 382 384 exceeded = true; /* Just break the loop */ 383 385 } 384 - /* avoid calling iput_final() while holding mdsc->snap_rwsem */ 385 - ceph_async_iput(in); 386 + iput(in); 386 387 387 388 next = realm->parent; 388 389 if (exceeded || !next)
+26 -19
fs/ceph/snap.c
··· 60 60 /* 61 61 * increase ref count for the realm 62 62 * 63 - * caller must hold snap_rwsem for write. 63 + * caller must hold snap_rwsem. 64 64 */ 65 65 void ceph_get_snap_realm(struct ceph_mds_client *mdsc, 66 66 struct ceph_snap_realm *realm) 67 67 { 68 + lockdep_assert_held(&mdsc->snap_rwsem); 69 + 68 70 dout("get_realm %p %d -> %d\n", realm, 69 71 atomic_read(&realm->nref), atomic_read(&realm->nref)+1); 70 72 /* ··· 115 113 { 116 114 struct ceph_snap_realm *realm; 117 115 116 + lockdep_assert_held_write(&mdsc->snap_rwsem); 117 + 118 118 realm = kzalloc(sizeof(*realm), GFP_NOFS); 119 119 if (!realm) 120 120 return ERR_PTR(-ENOMEM); ··· 139 135 /* 140 136 * lookup the realm rooted at @ino. 141 137 * 142 - * caller must hold snap_rwsem for write. 138 + * caller must hold snap_rwsem. 143 139 */ 144 140 static struct ceph_snap_realm *__lookup_snap_realm(struct ceph_mds_client *mdsc, 145 141 u64 ino) 146 142 { 147 143 struct rb_node *n = mdsc->snap_realms.rb_node; 148 144 struct ceph_snap_realm *r; 145 + 146 + lockdep_assert_held(&mdsc->snap_rwsem); 149 147 150 148 while (n) { 151 149 r = rb_entry(n, struct ceph_snap_realm, node); ··· 182 176 static void __destroy_snap_realm(struct ceph_mds_client *mdsc, 183 177 struct ceph_snap_realm *realm) 184 178 { 179 + lockdep_assert_held_write(&mdsc->snap_rwsem); 180 + 185 181 dout("__destroy_snap_realm %p %llx\n", realm, realm->ino); 186 182 187 183 rb_erase(&realm->node, &mdsc->snap_realms); ··· 206 198 static void __put_snap_realm(struct ceph_mds_client *mdsc, 207 199 struct ceph_snap_realm *realm) 208 200 { 201 + lockdep_assert_held_write(&mdsc->snap_rwsem); 202 + 209 203 dout("__put_snap_realm %llx %p %d -> %d\n", realm->ino, realm, 210 204 atomic_read(&realm->nref), atomic_read(&realm->nref)-1); 211 205 if (atomic_dec_and_test(&realm->nref)) ··· 246 236 { 247 237 struct ceph_snap_realm *realm; 248 238 239 + lockdep_assert_held_write(&mdsc->snap_rwsem); 240 + 249 241 spin_lock(&mdsc->snap_empty_lock); 250 242 while (!list_empty(&mdsc->snap_empty)) { 251 243 realm = list_first_entry(&mdsc->snap_empty, ··· 280 268 u64 parentino) 281 269 { 282 270 struct ceph_snap_realm *parent; 271 + 272 + lockdep_assert_held_write(&mdsc->snap_rwsem); 283 273 284 274 if (realm->parent_ino == parentino) 285 275 return 0; ··· 474 460 * Caller must hold snap_rwsem for read (i.e., the realm topology won't 475 461 * change). 476 462 */ 477 - void ceph_queue_cap_snap(struct ceph_inode_info *ci) 463 + static void ceph_queue_cap_snap(struct ceph_inode_info *ci) 478 464 { 479 465 struct inode *inode = &ci->vfs_inode; 480 466 struct ceph_cap_snap *capsnap; ··· 677 663 if (!inode) 678 664 continue; 679 665 spin_unlock(&realm->inodes_with_caps_lock); 680 - /* avoid calling iput_final() while holding 681 - * mdsc->snap_rwsem or in mds dispatch threads */ 682 - ceph_async_iput(lastinode); 666 + iput(lastinode); 683 667 lastinode = inode; 684 668 ceph_queue_cap_snap(ci); 685 669 spin_lock(&realm->inodes_with_caps_lock); 686 670 } 687 671 spin_unlock(&realm->inodes_with_caps_lock); 688 - ceph_async_iput(lastinode); 672 + iput(lastinode); 689 673 690 674 dout("queue_realm_cap_snaps %p %llx done\n", realm, realm->ino); 691 675 } ··· 707 695 int invalidate = 0; 708 696 int err = -ENOMEM; 709 697 LIST_HEAD(dirty_realms); 698 + 699 + lockdep_assert_held_write(&mdsc->snap_rwsem); 710 700 711 701 dout("update_snap_trace deletion=%d\n", deletion); 712 702 more: ··· 805 791 return 0; 806 792 807 793 bad: 808 - err = -EINVAL; 794 + err = -EIO; 809 795 fail: 810 796 if (realm && !IS_ERR(realm)) 811 797 ceph_put_snap_realm(mdsc, realm); ··· 837 823 ihold(inode); 838 824 spin_unlock(&mdsc->snap_flush_lock); 839 825 ceph_flush_snaps(ci, &session); 840 - /* avoid calling iput_final() while holding 841 - * session->s_mutex or in mds dispatch threads */ 842 - ceph_async_iput(inode); 826 + iput(inode); 843 827 spin_lock(&mdsc->snap_flush_lock); 844 828 } 845 829 spin_unlock(&mdsc->snap_flush_lock); 846 830 847 - if (session) { 848 - mutex_unlock(&session->s_mutex); 849 - ceph_put_mds_session(session); 850 - } 831 + ceph_put_mds_session(session); 851 832 dout("flush_snaps done\n"); 852 833 } 853 834 ··· 978 969 ceph_get_snap_realm(mdsc, realm); 979 970 ceph_put_snap_realm(mdsc, oldrealm); 980 971 981 - /* avoid calling iput_final() while holding 982 - * mdsc->snap_rwsem or mds in dispatch threads */ 983 - ceph_async_iput(inode); 972 + iput(inode); 984 973 continue; 985 974 986 975 skip_inode: 987 976 spin_unlock(&ci->i_ceph_lock); 988 - ceph_async_iput(inode); 977 + iput(inode); 989 978 } 990 979 991 980 /* we may have taken some of the old realm's children. */
-3
fs/ceph/super.h
··· 931 931 extern void ceph_handle_snap(struct ceph_mds_client *mdsc, 932 932 struct ceph_mds_session *session, 933 933 struct ceph_msg *msg); 934 - extern void ceph_queue_cap_snap(struct ceph_inode_info *ci); 935 934 extern int __ceph_finish_cap_snap(struct ceph_inode_info *ci, 936 935 struct ceph_cap_snap *capsnap); 937 936 extern void ceph_cleanup_empty_realms(struct ceph_mds_client *mdsc); ··· 987 988 988 989 extern bool ceph_inode_set_size(struct inode *inode, loff_t size); 989 990 extern void __ceph_do_pending_vmtruncate(struct inode *inode); 990 - 991 - extern void ceph_async_iput(struct inode *inode); 992 991 993 992 void ceph_queue_inode_work(struct inode *inode, int work_bit); 994 993
+1 -6
net/ceph/auth.c
··· 58 58 const int *con_modes) 59 59 { 60 60 struct ceph_auth_client *ac; 61 - int ret; 62 61 63 - ret = -ENOMEM; 64 62 ac = kzalloc(sizeof(*ac), GFP_NOFS); 65 63 if (!ac) 66 - goto out; 64 + return ERR_PTR(-ENOMEM); 67 65 68 66 mutex_init(&ac->mutex); 69 67 ac->negotiating = true; ··· 76 78 dout("%s name '%s' preferred_mode %d fallback_mode %d\n", __func__, 77 79 ac->name, ac->preferred_mode, ac->fallback_mode); 78 80 return ac; 79 - 80 - out: 81 - return ERR_PTR(ret); 82 81 } 83 82 84 83 void ceph_auth_destroy(struct ceph_auth_client *ac)
+2 -2
net/ceph/auth_none.c
··· 112 112 auth->authorizer = (struct ceph_authorizer *) au; 113 113 auth->authorizer_buf = au->buf; 114 114 auth->authorizer_buf_len = au->buf_len; 115 - auth->authorizer_reply_buf = au->reply_buf; 116 - auth->authorizer_reply_buf_len = sizeof (au->reply_buf); 115 + auth->authorizer_reply_buf = NULL; 116 + auth->authorizer_reply_buf_len = 0; 117 117 118 118 return 0; 119 119 }
-1
net/ceph/auth_none.h
··· 16 16 struct ceph_authorizer base; 17 17 char buf[128]; 18 18 int buf_len; 19 - char reply_buf[0]; 20 19 }; 21 20 22 21 struct ceph_auth_none_info {
+9 -3
net/ceph/cls_lock_client.c
··· 10 10 11 11 /** 12 12 * ceph_cls_lock - grab rados lock for object 13 - * @oid, @oloc: object to lock 13 + * @osdc: OSD client instance 14 + * @oid: object to lock 15 + * @oloc: object to lock 14 16 * @lock_name: the name of the lock 15 17 * @type: lock type (CEPH_CLS_LOCK_EXCLUSIVE or CEPH_CLS_LOCK_SHARED) 16 18 * @cookie: user-defined identifier for this instance of the lock ··· 84 82 85 83 /** 86 84 * ceph_cls_unlock - release rados lock for object 87 - * @oid, @oloc: object to lock 85 + * @osdc: OSD client instance 86 + * @oid: object to lock 87 + * @oloc: object to lock 88 88 * @lock_name: the name of the lock 89 89 * @cookie: user-defined identifier for this instance of the lock 90 90 */ ··· 134 130 135 131 /** 136 132 * ceph_cls_break_lock - release rados lock for object for specified client 137 - * @oid, @oloc: object to lock 133 + * @osdc: OSD client instance 134 + * @oid: object to lock 135 + * @oloc: object to lock 138 136 * @lock_name: the name of the lock 139 137 * @cookie: user-defined identifier for this instance of the lock 140 138 * @locker: current lock owner