| ... | ... | @@ -917,20 +917,18 @@ pub const BlameIterator = struct { |
| 917 | 917 | pub const Repository = struct { |
| 918 | 918 | gitdir: nfs.Dir, |
| 919 | 919 | gpa: std.mem.Allocator, |
| 920 | | raw_object_contents: std.StringArrayHashMapUnmanaged(RawObject), |
| 920 | unpacked_objects: std.StringArrayHashMapUnmanaged(GitObject), |
| 921 | 921 | idx_content: std.StringArrayHashMapUnmanaged([]const u8), |
| 922 | 922 | pack_content: std.StringArrayHashMapUnmanaged([]const u8), |
| 923 | 923 | commits: std.StringArrayHashMapUnmanaged(Commit), |
| 924 | 924 | trees: std.StringArrayHashMapUnmanaged(Tree), |
| 925 | 925 | tags: std.StringArrayHashMapUnmanaged(Tag), |
| 926 | 926 | |
| 927 | | const RawObject = struct { RefType, []const u8 }; |
| 928 | | |
| 929 | 927 | pub fn init(gitdir: nfs.Dir, gpa: std.mem.Allocator) Repository { |
| 930 | 928 | return .{ |
| 931 | 929 | .gitdir = gitdir, |
| 932 | 930 | .gpa = gpa, |
| 933 | | .raw_object_contents = .empty, |
| 931 | .unpacked_objects = .empty, |
| 934 | 932 | .idx_content = .empty, |
| 935 | 933 | .pack_content = .empty, |
| 936 | 934 | .commits = .empty, |
| ... | ... | @@ -940,8 +938,8 @@ pub const Repository = struct { |
| 940 | 938 | } |
| 941 | 939 | |
| 942 | 940 | pub fn deinit(r: *Repository) void { |
| 943 | | for (r.raw_object_contents.values()) |v| r.gpa.free(v[1]); |
| 944 | | r.raw_object_contents.deinit(r.gpa); |
| 941 | for (r.unpacked_objects.values()) |v| r.gpa.free(v.content); |
| 942 | r.unpacked_objects.deinit(r.gpa); |
| 945 | 943 | for (r.idx_content.values()) |v| nfs.munmap(v); |
| 946 | 944 | r.idx_content.deinit(r.gpa); |
| 947 | 945 | for (r.pack_content.values()) |v| nfs.munmap(v); |
| ... | ... | @@ -952,9 +950,9 @@ pub const Repository = struct { |
| 952 | 950 | r.tags.deinit(r.gpa); |
| 953 | 951 | } |
| 954 | 952 | |
| 955 | | fn getObject(r: *Repository, oid: Id, arena: std.mem.Allocator) !?RawObject { |
| 956 | | if (r.raw_object_contents.get(oid)) |data| { |
| 957 | | return data; |
| 953 | pub fn getObject(r: *Repository, arena: std.mem.Allocator, oid: Id) !?GitObject { |
| 954 | if (r.unpacked_objects.get(oid)) |obj| { |
| 955 | return obj; |
| 958 | 956 | } |
| 959 | 957 | if (oid.len == 40) blk: { //sha1 object |
| 960 | 958 | var sub_path: [49:0]u8 = "objects/00/00000000000000000000000000000000000000".*; |
| ... | ... | @@ -978,8 +976,9 @@ pub const Repository = struct { |
| 978 | 976 | list.replaceRangeAssumeCapacity(0, header.len + 1, ""); |
| 979 | 977 | const content = try list.toOwnedSlice(); |
| 980 | 978 | std.debug.assert(content.len == content_len); |
| 981 | | try r.raw_object_contents.put(r.gpa, oid, .{ _type, content }); |
| 982 | | return .{ _type, content }; |
| 979 | const obj: GitObject = .{ .type = _type, .content = content }; |
| 980 | try r.unpacked_objects.put(r.gpa, oid, obj); |
| 981 | return obj; |
| 983 | 982 | } |
| 984 | 983 | |
| 985 | 984 | // read .idx |
| ... | ... | @@ -1043,7 +1042,7 @@ pub const Repository = struct { |
| 1043 | 1042 | return try r.getPackedObject(oid, pack_index, pack_offset); |
| 1044 | 1043 | } |
| 1045 | 1044 | |
| 1046 | | fn getPackedObject(r: *Repository, maybe_oid: ?Id, pack_index: usize, pack_offset: usize) !RawObject { |
| 1045 | fn getPackedObject(r: *Repository, maybe_oid: ?Id, pack_index: usize, pack_offset: usize) !GitObject { |
| 1047 | 1046 | const pack_content = r.pack_content.values()[pack_index]; |
| 1048 | 1047 | if (!std.mem.eql(u8, pack_content[0..4], "PACK")) return error.InvalidGitPack; |
| 1049 | 1048 | const pack_version = std.mem.readInt(u32, pack_content[4..][0..4], .big); |
| ... | ... | @@ -1082,8 +1081,9 @@ pub const Repository = struct { |
| 1082 | 1081 | try std.compress.flate.inflate.decompress(.zlib, bufr.anyReadable(), list.writer()); |
| 1083 | 1082 | const _type = std.meta.stringToEnum(RefType, @tagName(ty)).?; |
| 1084 | 1083 | const content = try list.toOwnedSlice(); |
| 1085 | | if (maybe_oid) |oid| try r.raw_object_contents.put(r.gpa, oid, .{ _type, content }); |
| 1086 | | return .{ _type, content }; |
| 1084 | const obj: GitObject = .{ .type = _type, .content = content }; |
| 1085 | if (maybe_oid) |oid| try r.unpacked_objects.put(r.gpa, oid, obj); |
| 1086 | return obj; |
| 1087 | 1087 | }, |
| 1088 | 1088 | .ofs_delta => { |
| 1089 | 1089 | std.log.debug("type={s} size={d}", .{ @tagName(ty), size }); |
| ... | ... | @@ -1103,14 +1103,6 @@ pub const Repository = struct { |
| 1103 | 1103 | } |
| 1104 | 1104 | } |
| 1105 | 1105 | |
| 1106 | | pub fn getGitObject(r: *Repository, arena: std.mem.Allocator, oid: Id) !?GitObject { |
| 1107 | | if (try r.getObject(oid, arena)) |data| { |
| 1108 | | const _type, const content = data; |
| 1109 | | return .{ .type = _type, .content = content }; |
| 1110 | | } |
| 1111 | | return null; |
| 1112 | | } |
| 1113 | | |
| 1114 | 1106 | const GitObject = struct { |
| 1115 | 1107 | type: RefType, |
| 1116 | 1108 | content: []const u8, |
| ... | ... | @@ -1120,7 +1112,7 @@ pub const Repository = struct { |
| 1120 | 1112 | if (r.commits.getPtr(id.id)) |val| { |
| 1121 | 1113 | return .{ id, val.* }; |
| 1122 | 1114 | } |
| 1123 | | if (try r.getGitObject(arena, id.id)) |obj| { |
| 1115 | if (try r.getObject(arena, id.id)) |obj| { |
| 1124 | 1116 | if (obj.type == .commit) { |
| 1125 | 1117 | const commit = try parseCommit(arena, obj.content); |
| 1126 | 1118 | try r.commits.put(r.gpa, id.id, commit); |
| ... | ... | @@ -1134,7 +1126,7 @@ pub const Repository = struct { |
| 1134 | 1126 | if (r.trees.getPtr(id.id)) |val| { |
| 1135 | 1127 | return .{ id, val.* }; |
| 1136 | 1128 | } |
| 1137 | | if (try r.getGitObject(arena, id.id)) |obj| { |
| 1129 | if (try r.getObject(arena, id.id)) |obj| { |
| 1138 | 1130 | if (obj.type == .tree) { |
| 1139 | 1131 | var children = std.ArrayList(Tree.Object).init(r.gpa); |
| 1140 | 1132 | errdefer children.deinit(); |
| ... | ... | @@ -1181,7 +1173,7 @@ pub const Repository = struct { |
| 1181 | 1173 | if (r.tags.getPtr(id.id)) |val| { |
| 1182 | 1174 | return .{ id, val.* }; |
| 1183 | 1175 | } |
| 1184 | | if (try r.getGitObject(arena, id.id)) |obj| { |
| 1176 | if (try r.getObject(arena, id.id)) |obj| { |
| 1185 | 1177 | if (obj.type == .tag) { |
| 1186 | 1178 | const tag = try parseTag(obj.content); |
| 1187 | 1179 | try r.tags.put(r.gpa, id.id, tag); |