diff options
| author | Paul Donald | 2025-11-09 15:11:46 +0000 |
|---|---|---|
| committer | Robert Marko | 2025-11-10 14:14:21 +0000 |
| commit | 483263c7b0cd3922b93be2cf9dad5eeccbb9fedb (patch) | |
| tree | 41d13ea01274106cfec07372dfa845b8c4efef2a | |
| parent | 917000075eb48c934f0a456be3b884758c376e0b (diff) | |
| download | rpcd-483263c7b0cd3922b93be2cf9dad5eeccbb9fedb.tar.gz | |
file: append "target" for symbolic links
When list encounters a symbolic link, we add its nested "target" entry, to where
the symbolic link points. Just how `ls -l` reports.
So when calling e.g.: ubus call file list '{"path":"/etc"}'
instead of:
...
"name": "os-release",
"type": "symlink",
"size": 21,
"mode": 41471,
"atime": 1760891865,
"mtime": 1760891865,
"ctime": 1760891865,
"inode": 266,
"uid": 0,
"gid": 0,
"target_type": "file"
...
We get:
...
"name": "os-release",
"type": "symlink",
"size": 21,
"mode": 41471,
"atime": 1760891865,
"mtime": 1760891865,
"ctime": 1760891865,
"inode": 266,
"uid": 0,
"gid": 0,
"target": {
"name": "../usr/lib/os-release",
"type": "file",
"size": 582,
"mode": 33188,
"atime": 1760891865,
"mtime": 1760891865,
"ctime": 1760891865,
"inode": 1744,
"uid": 0,
"gid": 0
}
...
And should a link be broken:
"name": "foo",
"type": "symlink",
"size": 8,
"mode": 41471,
"atime": 1762640365,
"mtime": 1762640365,
"ctime": 1762640365,
"inode": 348,
"uid": 0,
"gid": 0,
"target": {
"name": "/tmp/foo",
"type": "broken"
}
Tested on: OpenWrt 24.10.4 r28959-29397011cc
Signed-off-by: Paul Donald <newtwen+github@gmail.com>
Tested-by: Eric Fahlgren <ericfahlgren@gmail.com>
Link: https://github.com/openwrt/rpcd/pull/21
Signed-off-by: Robert Marko <robimarko@gmail.com>
| -rw-r--r-- | file.c | 18 |
1 files changed, 16 insertions, 2 deletions
@@ -537,12 +537,26 @@ rpc_file_list(struct ubus_context *ctx, struct ubus_object *obj, // add target type only for symlinks if (S_ISLNK(s.st_mode)) { + char tbuf[PATH_MAX + 1]; + ssize_t tlen; + void *t; + + // open nested table "target" for symbolic link + t = blobmsg_open_table(&buf, "target"); + + tlen = readlink(entrypath, tbuf, sizeof(tbuf) - 1); + if (tlen >= 0) { + tbuf[tlen] = '\0'; + } + blobmsg_add_string(&buf, "name", tbuf); + struct stat target; if (!stat(entrypath, &target)) { - blobmsg_add_string(&buf, "target_type", d_types[_get_stat_type(&target)]); + _rpc_file_add_stat(&target); } else { - blobmsg_add_string(&buf, "target_type", "broken"); + blobmsg_add_string(&buf, "type", "broken"); } + blobmsg_close_table(&buf, t); } blobmsg_close_table(&buf, d); } |