Skip to content

Commit cfac7ef

Browse files
committed
Merge PR ceph#56776 into main
* refs/pull/56776/head: client: fix d_reclen for readdir Reviewed-by: Patrick Donnelly <[email protected]>
2 parents 3474820 + 5ac0165 commit cfac7ef

File tree

1 file changed

+9
-3
lines changed

1 file changed

+9
-3
lines changed

src/client/Client.cc

Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@
1414

1515

1616
// unix-ey fs stuff
17+
#include <algorithm>
1718
#include <unistd.h>
1819
#include <sys/types.h>
1920
#include <time.h>
@@ -9275,14 +9276,19 @@ void Client::seekdir(dir_result_t *dirp, loff_t offset)
92759276
//};
92769277
void Client::fill_dirent(struct dirent *de, const char *name, int type, uint64_t ino, loff_t next_off)
92779278
{
9278-
strncpy(de->d_name, name, 255);
9279-
de->d_name[255] = '\0';
9279+
size_t len = strlen(name);
9280+
len = std::min(len, (size_t)255);
9281+
memcpy(de->d_name, name, len);
9282+
de->d_name[len] = '\0';
92809283
#if !defined(__CYGWIN__) && !(defined(_WIN32))
92819284
de->d_ino = ino;
92829285
#if !defined(__APPLE__) && !defined(__FreeBSD__)
92839286
de->d_off = next_off;
92849287
#endif
9285-
de->d_reclen = 1;
9288+
// Calculate the real used size of the record
9289+
len = (uintptr_t)&de->d_name[len] - (uintptr_t)de + 1;
9290+
// The record size must be a multiple of the alignment of 'struct dirent'
9291+
de->d_reclen = (len + alignof(struct dirent) - 1) & ~(alignof(struct dirent) - 1);
92869292
de->d_type = IFTODT(type);
92879293
ldout(cct, 10) << __func__ << " '" << de->d_name << "' -> " << inodeno_t(de->d_ino)
92889294
<< " type " << (int)de->d_type << " w/ next_off " << hex << next_off << dec << dendl;

0 commit comments

Comments
 (0)