diff options
Diffstat (limited to 'net/9p')
-rw-r--r-- | net/9p/client.c | 47 | ||||
-rw-r--r-- | net/9p/protocol.c | 27 |
2 files changed, 74 insertions, 0 deletions
diff --git a/net/9p/client.c b/net/9p/client.c index 37c8da07a80b..a80357483a47 100644 --- a/net/9p/client.c +++ b/net/9p/client.c | |||
@@ -1432,3 +1432,50 @@ error: | |||
1432 | } | 1432 | } |
1433 | EXPORT_SYMBOL(p9_client_rename); | 1433 | EXPORT_SYMBOL(p9_client_rename); |
1434 | 1434 | ||
1435 | int p9_client_readdir(struct p9_fid *fid, char *data, u32 count, u64 offset) | ||
1436 | { | ||
1437 | int err, rsize, total; | ||
1438 | struct p9_client *clnt; | ||
1439 | struct p9_req_t *req; | ||
1440 | char *dataptr; | ||
1441 | |||
1442 | P9_DPRINTK(P9_DEBUG_9P, ">>> TREADDIR fid %d offset %llu count %d\n", | ||
1443 | fid->fid, (long long unsigned) offset, count); | ||
1444 | |||
1445 | err = 0; | ||
1446 | clnt = fid->clnt; | ||
1447 | total = 0; | ||
1448 | |||
1449 | rsize = fid->iounit; | ||
1450 | if (!rsize || rsize > clnt->msize-P9_READDIRHDRSZ) | ||
1451 | rsize = clnt->msize - P9_READDIRHDRSZ; | ||
1452 | |||
1453 | if (count < rsize) | ||
1454 | rsize = count; | ||
1455 | |||
1456 | req = p9_client_rpc(clnt, P9_TREADDIR, "dqd", fid->fid, offset, rsize); | ||
1457 | if (IS_ERR(req)) { | ||
1458 | err = PTR_ERR(req); | ||
1459 | goto error; | ||
1460 | } | ||
1461 | |||
1462 | err = p9pdu_readf(req->rc, clnt->proto_version, "D", &count, &dataptr); | ||
1463 | if (err) { | ||
1464 | p9pdu_dump(1, req->rc); | ||
1465 | goto free_and_error; | ||
1466 | } | ||
1467 | |||
1468 | P9_DPRINTK(P9_DEBUG_9P, "<<< RREADDIR count %d\n", count); | ||
1469 | |||
1470 | if (data) | ||
1471 | memmove(data, dataptr, count); | ||
1472 | |||
1473 | p9_free_req(clnt, req); | ||
1474 | return count; | ||
1475 | |||
1476 | free_and_error: | ||
1477 | p9_free_req(clnt, req); | ||
1478 | error: | ||
1479 | return err; | ||
1480 | } | ||
1481 | EXPORT_SYMBOL(p9_client_readdir); | ||
diff --git a/net/9p/protocol.c b/net/9p/protocol.c index 149f82160130..b645c8263538 100644 --- a/net/9p/protocol.c +++ b/net/9p/protocol.c | |||
@@ -580,3 +580,30 @@ void p9pdu_reset(struct p9_fcall *pdu) | |||
580 | pdu->offset = 0; | 580 | pdu->offset = 0; |
581 | pdu->size = 0; | 581 | pdu->size = 0; |
582 | } | 582 | } |
583 | |||
584 | int p9dirent_read(char *buf, int len, struct p9_dirent *dirent, | ||
585 | int proto_version) | ||
586 | { | ||
587 | struct p9_fcall fake_pdu; | ||
588 | int ret; | ||
589 | char *nameptr; | ||
590 | |||
591 | fake_pdu.size = len; | ||
592 | fake_pdu.capacity = len; | ||
593 | fake_pdu.sdata = buf; | ||
594 | fake_pdu.offset = 0; | ||
595 | |||
596 | ret = p9pdu_readf(&fake_pdu, proto_version, "Qqbs", &dirent->qid, | ||
597 | &dirent->d_off, &dirent->d_type, &nameptr); | ||
598 | if (ret) { | ||
599 | P9_DPRINTK(P9_DEBUG_9P, "<<< p9dirent_read failed: %d\n", ret); | ||
600 | p9pdu_dump(1, &fake_pdu); | ||
601 | goto out; | ||
602 | } | ||
603 | |||
604 | strcpy(dirent->d_name, nameptr); | ||
605 | |||
606 | out: | ||
607 | return fake_pdu.offset; | ||
608 | } | ||
609 | EXPORT_SYMBOL(p9dirent_read); | ||