ls but with io_uring

use getpwuid and getgrgid if user/group is not found

authored by chinmay.srht.site and committed by rockorager.dev bbd03ced cb16ce70

+36 -10
+1
build.zig
··· 45 .name = "lsr", 46 .root_module = exe_mod, 47 }); 48 49 b.installArtifact(exe); 50
··· 45 .name = "lsr", 46 .root_module = exe_mod, 47 }); 48 + exe.linkLibC(); 49 50 b.installArtifact(exe); 51
+35 -10
src/main.zig
··· 4 const zeit = @import("zeit"); 5 const natord = @import("natord.zig"); 6 const build_options = @import("build_options"); 7 8 const posix = std.posix; 9 ··· 343 if (multiple_dirs and dir_idx > 0) try bw.writer().writeAll("\r\n"); 344 try printTree(cmd, bw.writer()); 345 } else if (cmd.opts.long) { 346 - try printLong(cmd, bw.writer()); 347 } else switch (cmd.opts.shortview) { 348 .columns => try printShortColumns(cmd, bw.writer()), 349 .oneline => try printShortOnePerLine(cmd, bw.writer()), ··· 537 } 538 539 fn recurseTree(cmd: Command, writer: anytype, dir_path: [:0]const u8, prefix_list: *std.ArrayList(bool), depth: usize, max_depth: usize) !void { 540 - var dir = std.fs.cwd().openDir(dir_path, .{ .iterate = true }) catch { return; }; 541 defer dir.close(); 542 543 var entries = std.ArrayList(Entry).init(cmd.arena); 544 var iter = dir.iterate(); 545 - 546 while (try iter.next()) |dirent| { 547 if (!cmd.opts.showDotfiles() and std.mem.startsWith(u8, dirent.name, ".")) continue; 548 ··· 622 } 623 } 624 625 - fn printLong(cmd: Command, writer: anytype) !void { 626 const tz = cmd.tz.?; 627 const now = zeit.instant(.{}) catch unreachable; 628 const one_year_ago = try now.subtract(.{ .days = 365 }); ··· 634 var n_size: usize = 0; 635 var n_suff: usize = 0; 636 for (cmd.entries) |entry| { 637 - const group = cmd.getGroup(entry.statx.gid); 638 - const user = cmd.getUser(entry.statx.uid); 639 640 var buf: [16]u8 = undefined; 641 const size = try entry.humanReadableSize(&buf); ··· 666 }; 667 668 for (cmd.entries) |entry| { 669 - const user: User = cmd.getUser(entry.statx.uid) orelse 670 .{ 671 .uid = entry.statx.uid, 672 .name = try std.fmt.allocPrint(cmd.arena, "{d}", .{entry.statx.uid}), 673 }; 674 - const group: Group = cmd.getGroup(entry.statx.gid) orelse 675 .{ 676 .gid = entry.statx.gid, 677 .name = try std.fmt.allocPrint(cmd.arena, "{d}", .{entry.statx.gid}), ··· 788 groups: std.ArrayListUnmanaged(Group) = .empty, 789 users: std.ArrayListUnmanaged(User) = .empty, 790 791 - fn getUser(self: Command, uid: posix.uid_t) ?User { 792 for (self.users.items) |user| { 793 if (user.uid == uid) return user; 794 } 795 return null; 796 } 797 798 - fn getGroup(self: Command, gid: posix.gid_t) ?Group { 799 for (self.groups.items) |group| { 800 if (group.gid == gid) return group; 801 } 802 return null; 803 }
··· 4 const zeit = @import("zeit"); 5 const natord = @import("natord.zig"); 6 const build_options = @import("build_options"); 7 + const grp = @cImport({ 8 + @cInclude("grp.h"); 9 + }); 10 11 const posix = std.posix; 12 ··· 346 if (multiple_dirs and dir_idx > 0) try bw.writer().writeAll("\r\n"); 347 try printTree(cmd, bw.writer()); 348 } else if (cmd.opts.long) { 349 + try printLong(&cmd, bw.writer()); 350 } else switch (cmd.opts.shortview) { 351 .columns => try printShortColumns(cmd, bw.writer()), 352 .oneline => try printShortOnePerLine(cmd, bw.writer()), ··· 540 } 541 542 fn recurseTree(cmd: Command, writer: anytype, dir_path: [:0]const u8, prefix_list: *std.ArrayList(bool), depth: usize, max_depth: usize) !void { 543 + var dir = std.fs.cwd().openDir(dir_path, .{ .iterate = true }) catch { 544 + return; 545 + }; 546 defer dir.close(); 547 548 var entries = std.ArrayList(Entry).init(cmd.arena); 549 var iter = dir.iterate(); 550 + 551 while (try iter.next()) |dirent| { 552 if (!cmd.opts.showDotfiles() and std.mem.startsWith(u8, dirent.name, ".")) continue; 553 ··· 627 } 628 } 629 630 + fn printLong(cmd: *Command, writer: anytype) !void { 631 const tz = cmd.tz.?; 632 const now = zeit.instant(.{}) catch unreachable; 633 const one_year_ago = try now.subtract(.{ .days = 365 }); ··· 639 var n_size: usize = 0; 640 var n_suff: usize = 0; 641 for (cmd.entries) |entry| { 642 + const group = try cmd.getGroup(entry.statx.gid); 643 + const user = try cmd.getUser(entry.statx.uid); 644 645 var buf: [16]u8 = undefined; 646 const size = try entry.humanReadableSize(&buf); ··· 671 }; 672 673 for (cmd.entries) |entry| { 674 + const user: User = try cmd.getUser(entry.statx.uid) orelse 675 .{ 676 .uid = entry.statx.uid, 677 .name = try std.fmt.allocPrint(cmd.arena, "{d}", .{entry.statx.uid}), 678 }; 679 + const group: Group = try cmd.getGroup(entry.statx.gid) orelse 680 .{ 681 .gid = entry.statx.gid, 682 .name = try std.fmt.allocPrint(cmd.arena, "{d}", .{entry.statx.gid}), ··· 793 groups: std.ArrayListUnmanaged(Group) = .empty, 794 users: std.ArrayListUnmanaged(User) = .empty, 795 796 + fn getUser(self: *Command, uid: posix.uid_t) !?User { 797 for (self.users.items) |user| { 798 if (user.uid == uid) return user; 799 } 800 + const user_nullable = std.c.getpwuid(uid); 801 + if (user_nullable) |user| { 802 + if (user.name) |name| { 803 + const new_user = User{ 804 + .uid = uid, 805 + .name = std.mem.span(name), 806 + }; 807 + try self.users.append(self.arena, new_user); 808 + return new_user; 809 + } 810 + } 811 return null; 812 } 813 814 + fn getGroup(self: *Command, gid: posix.gid_t) !?Group { 815 for (self.groups.items) |group| { 816 if (group.gid == gid) return group; 817 + } 818 + const grp_group_nullable = grp.getgrgid(gid); 819 + if (grp_group_nullable) |grp_group_ptr| { 820 + const new_group = Group{ 821 + .gid = gid, 822 + .name = std.mem.span(grp_group_ptr.*.gr_name), 823 + }; 824 + try self.groups.append(self.arena, new_group); 825 + return new_group; 826 } 827 return null; 828 }