| 8332 | } |
| 8333 | |
| 8334 | int Client::_getvxattr( |
| 8335 | Inode *in, |
| 8336 | const UserPerm& perms, |
| 8337 | const char *xattr_name, |
| 8338 | ssize_t size, |
| 8339 | void *value, |
| 8340 | mds_rank_t rank) |
| 8341 | { |
| 8342 | if (!xattr_name || strlen(xattr_name) <= 0 || strlen(xattr_name) > 255) { |
| 8343 | return -ENODATA; |
| 8344 | } |
| 8345 | |
| 8346 | MetaRequest *req = new MetaRequest(CEPH_MDS_OP_GETVXATTR); |
| 8347 | filepath path; |
| 8348 | in->make_nosnap_relative_path(path); |
| 8349 | req->set_filepath(path); |
| 8350 | req->set_inode(in); |
| 8351 | req->set_string2(xattr_name); |
| 8352 | |
| 8353 | bufferlist bl; |
| 8354 | int res = make_request(req, perms, nullptr, nullptr, rank, &bl, |
| 8355 | CEPHFS_FEATURE_OP_GETVXATTR); |
| 8356 | ldout(cct, 10) << __func__ << " result=" << res << dendl; |
| 8357 | |
| 8358 | if (res < 0) { |
| 8359 | if (res == -EOPNOTSUPP) { |
| 8360 | return -ENODATA; |
| 8361 | } |
| 8362 | return res; |
| 8363 | } |
| 8364 | |
| 8365 | std::string buf; |
| 8366 | auto p = bl.cbegin(); |
| 8367 | |
| 8368 | DECODE_START(1, p); |
| 8369 | decode(buf, p); |
| 8370 | DECODE_FINISH(p); |
| 8371 | |
| 8372 | ssize_t len = buf.length(); |
| 8373 | |
| 8374 | res = len; // refer to man getxattr(2) for output buffer size == 0 |
| 8375 | |
| 8376 | if (size > 0) { |
| 8377 | if (len > size) { |
| 8378 | res = -ERANGE; // insufficient output buffer space |
| 8379 | } else { |
| 8380 | memcpy(value, buf.c_str(), len); |
| 8381 | } |
| 8382 | } |
| 8383 | return res; |
| 8384 | } |
| 8385 | |
| 8386 | bool Client::make_absolute_path_string(const InodeRef& in, std::string& path) |
| 8387 | { |
nothing calls this directly
no test coverage detected