Permalink
Find file
Fetching contributors…
Cannot retrieve contributors at this time
174 lines (150 sloc) 6.23 KB
using Nemerle.Collections;
using Nemerle.Text;
using Nemerle.Utility;
using Tests.Macros;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Security.Cryptography;
using Tao;
namespace Tests
{
public class MSDosHeaderTests
{
private mutable _inputStream : System.IO.Stream;
public Setup() : void
{
_inputStream = System.IO.FileStream(@"..\..\SampleBinaries\Skeleton.exe", FileMode.Open);
}
public Teardown() : void
{
_inputStream.Close();
_inputStream.Dispose();
}
public ShouldBeAbleToExtractDosHeaderBlockAsFirst128Bytes() : void
{
def reader = DosHeaderReader();
// Verify the read block length is 128 bytes
def dosHeader = reader.Read(_inputStream);
def headerStream : System.IO.Stream = dosHeader.Data;
// Verify the hash matches the manually calculated hash of the skeleton binary
def binaryReader = BinaryReader(headerStream);
def bytesRead = binaryReader.ReadBytes(headerStream.Length :> System.Int32);
def currentHash = bytesRead.GetHash();
def expectedHash = "D1-79-60-D4-11-9D-47-57-44-58-87-0D-FB-13-94-C3-F9-50-B0-C8-C1-2D-61-90-DE-6C-AC-52-75-89-4D-26-B8-5A-7C-C0-69-9F-1E-20-D5-5B-D0-97-13-5F-89-16-22-26-D9-54-10-6F-DC-E0-87-E1-27-FC-0E-98-6D-D9";
assert headerStream.Length equals 128 otherwiseprint "Invalid header stream length";
assert expectedHash equals currentHash otherwiseprint "Wrong Hash Code";
}
public ShouldThrowBadImageExceptionIfStreamIsLessThan128Bytes() : void
expects BadImageFormatException
{
def bytes = array[0x4d : byte, 0x5a];
def stream = MemoryStream(bytes);
def reader = DosHeaderReader();
_ = reader.Read(stream);
}
public ShouldThrowBadImageFormatExceptionIfHeaderDoesNotStartWithMZ() : void
expects BadImageFormatException
{
def bytes = array[ // invalid dos header start
0x01 : byte, 0x2a, 0x90, 0x00, 0x03, 0x00, 0x00,
0x00, 0x04, 0x00, 0x00, 0x00, 0xff, 0xff,
0x00, 0x00, 0xb8, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00,
// lfanew
0x80, 0x00, 0x00, 0x00,
// dos header end
0x0e, 0x1f, 0xba, 0x0e, 0x00, 0xb4, 0x09,
0xcd, 0x21, 0xb8, 0x01, 0x4c, 0xcd, 0x21,
0x54, 0x68, 0x69, 0x73, 0x20, 0x70, 0x72,
0x6f, 0x67, 0x72, 0x61, 0x6d, 0x20, 0x63,
0x61, 0x6e, 0x6e, 0x6f, 0x74, 0x20, 0x62,
0x65, 0x20, 0x72, 0x75, 0x6e, 0x20, 0x69,
0x6e, 0x20, 0x44, 0x4f, 0x53, 0x20, 0x6d,
0x6f, 0x64, 0x65, 0x2e, 0x0d, 0x0d, 0x0a,
0x24, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00];
def stream = MemoryStream(bytes);
def reader = DosHeaderReader();
_ = reader.Read(stream);
}
public ShouldWriteLfaNewValue() : void
{
def bytes = array[ // dos header start
0x4d : byte, 0x5a, 0x90, 0x00, 0x03, 0x00, 0x00,
0x00, 0x04, 0x00, 0x00, 0x00, 0xff, 0xff,
0x00, 0x00, 0xb8, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00,
// lfanew
0x80, 0x00, 0x00, 0x00,
// dos header end
0x0e, 0x1f, 0xba, 0x0e, 0x00, 0xb4, 0x09,
0xcd, 0x21, 0xb8, 0x01, 0x4c, 0xcd, 0x21,
0x54, 0x68, 0x69, 0x73, 0x20, 0x70, 0x72,
0x6f, 0x67, 0x72, 0x61, 0x6d, 0x20, 0x63,
0x61, 0x6e, 0x6e, 0x6f, 0x74, 0x20, 0x62,
0x65, 0x20, 0x72, 0x75, 0x6e, 0x20, 0x69,
0x6e, 0x20, 0x44, 0x4f, 0x53, 0x20, 0x6d,
0x6f, 0x64, 0x65, 0x2e, 0x0d, 0x0d, 0x0a,
0x24, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00];
def headerStream = MemoryStream(bytes);
def header = DosHeader(headerStream);
header.LfaNew = 0xF0;
def outputStream = MemoryStream();
def writer = DosHeaderWriter();
writer.Write(header, outputStream);
// The written output stream should have the correct LfaNew value
_ = outputStream.Seek(0x3C, SeekOrigin.Begin);
def reader = BinaryReader(outputStream);
def actualLfaNew = reader.ReadUInt32();
assert actualLfaNew equals header.LfaNew otherwiseprint "Invalid LfaNew value";
}
public ShouldMatchGivenHeaderBytesWhenWrittenToTargetStream() : void
{
def bytes = array[ // dos header start
0x4d : byte, 0x5a, 0x90, 0x00, 0x03, 0x00, 0x00,
0x00, 0x04, 0x00, 0x00, 0x00, 0xff, 0xff,
0x00, 0x00, 0xb8, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00,
// lfanew
0x80, 0x00, 0x00, 0x00,
// dos header end
0x0e, 0x1f, 0xba, 0x0e, 0x00, 0xb4, 0x09,
0xcd, 0x21, 0xb8, 0x01, 0x4c, 0xcd, 0x21,
0x54, 0x68, 0x69, 0x73, 0x20, 0x70, 0x72,
0x6f, 0x67, 0x72, 0x61, 0x6d, 0x20, 0x63,
0x61, 0x6e, 0x6e, 0x6f, 0x74, 0x20, 0x62,
0x65, 0x20, 0x72, 0x75, 0x6e, 0x20, 0x69,
0x6e, 0x20, 0x44, 0x4f, 0x53, 0x20, 0x6d,
0x6f, 0x64, 0x65, 0x2e, 0x0d, 0x0d, 0x0a,
0x24, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00];
def expectedHash = bytes.GetHash();
def writer = DosHeaderWriter();
def outputStream = MemoryStream();
def outputBytes = array(bytes.Length) : array[byte];
def dosHeader = DosHeader(MemoryStream(bytes));
writer.Write(dosHeader, outputStream);
_ = outputStream.Read(outputBytes, 0, bytes.Length);
def actualHash = outputStream.GetHash();
assert expectedHash equals actualHash otherwiseprint "Invalid DOS header";
}
}
}