internal ObjectId WriteObject(ObjectType type, long len, Stream input, bool store)
{
FileInfo info;
DeflaterOutputStream stream;
FileStream stream2;
ObjectId objectId = null;
if (store)
{
info = _r.ObjectsDirectory.CreateTempFile("noz");
stream2 = info.OpenWrite();
}
else
{
info = null;
stream2 = null;
}
_md.Reset();
if (store)
{
_def.Reset();
stream = new DeflaterOutputStream(stream2, _def);
}
else
{
stream = null;
}
try
{
int num;
byte[] bytes = Codec.EncodedTypeString(type);
_md.Update(bytes);
if (stream != null)
{
stream.Write(bytes, 0, bytes.Length);
}
_md.Update(0x20);
if (stream != null)
{
stream.WriteByte(0x20);
}
bytes = Constants.encodeASCII(len.ToString());
_md.Update(bytes);
if (stream != null)
{
stream.Write(bytes, 0, bytes.Length);
}
_md.Update(0);
if (stream != null)
{
stream.WriteByte(0);
}
while ((len > 0L) && ((num = input.Read(_buf, 0, (int) Math.Min(len, _buf.Length))) > 0))
{
_md.Update(_buf, 0, num);
if (stream != null)
{
stream.Write(_buf, 0, num);
}
len -= num;
}
if (len != 0L)
{
throw new IOException("Input did not match supplied Length. " + len + " bytes are missing.");
}
if (stream != null)
{
stream.Close();
if (info != null)
{
info.IsReadOnly = true;
}
}
objectId = ObjectId.FromRaw(_md.Digest());
}
finally
{
if ((objectId == null) && (stream != null))
{
try
{
stream.Close();
}
finally
{
info.DeleteFile();
}
}
}
if (info != null)
{
if (_r.HasObject(objectId))
{
// Object is already in the repository so remove
// the temporary file.
//
info.DeleteFile();
}
else
{
FileInfo info2 = _r.ToFile(objectId);
if (!info.RenameTo(info2.FullName))
{
// Maybe the directory doesn't exist yet as the object
// directories are always lazily created. Note that we
// try the rename first as the directory likely does exist.
//
if (info2.Directory != null)
{
info2.Directory.Create();
}
if (!info.RenameTo(info2.FullName) && !_r.HasObject(objectId))
{
// The object failed to be renamed into its proper
// location and it doesn't exist in the repository
// either. We really don't know what went wrong, so
// fail.
//
info.DeleteFile();
throw new ObjectWritingException("Unable to create new object: " + info2);
}
}
}
}
return objectId;
}