/// <summary>Construct and write tree out of index.</summary> /// <remarks>Construct and write tree out of index.</remarks> /// <returns>SHA-1 of the constructed tree</returns> /// <exception cref="System.IO.IOException">System.IO.IOException</exception> public virtual ObjectId WriteTree() { CheckWriteOk(); ObjectInserter inserter = db.NewObjectInserter(); try { Tree current = new Tree(db); Stack <Tree> trees = new Stack <Tree>(); trees.Push(current); string[] prevName = new string[0]; foreach (GitIndex.Entry e in entries.Values) { if (e.GetStage() != 0) { continue; } string[] newName = SplitDirPath(e.GetName()); int c = LongestCommonPath(prevName, newName); while (c < trees.Count - 1) { current.SetId(inserter.Insert(Constants.OBJ_TREE, current.Format())); trees.Pop(); current = trees.IsEmpty() ? null : (Tree)trees.Peek(); } while (trees.Count < newName.Length) { if (!current.ExistsTree(newName[trees.Count - 1])) { current = new Tree(current, Constants.Encode(newName[trees.Count - 1])); current.GetParent().AddEntry(current); trees.Push(current); } else { current = (Tree)current.FindTreeMember(newName[trees.Count - 1]); trees.Push(current); } } FileTreeEntry ne = new FileTreeEntry(current, e.sha1, Constants.Encode(newName[newName .Length - 1]), (e.mode & FileMode.EXECUTABLE_FILE.GetBits()) == FileMode.EXECUTABLE_FILE .GetBits()); current.AddEntry(ne); } while (!trees.IsEmpty()) { current.SetId(inserter.Insert(Constants.OBJ_TREE, current.Format())); trees.Pop(); if (!trees.IsEmpty()) { current = trees.Peek(); } } inserter.Flush(); return(current.GetId()); } finally { inserter.Release(); } }