//
// Copyright (c) 2002
// Ronald Kevin Burton
//
// Z poniższym kodem nie jest związana żadna gwarancja poprawności działania.
// Program został dołączony do książki ".NET CLR. Księga eksperta" w celu
// ilustracji koncepcji i zasad przedstawionych w tej książce. Program może być 
// używany na własne ryzyko.
//
// Przyznaje się prawo do użycia lub kopiowania tego oprogramowania do dowolnego celu
// bez konieczności ponoszenia żadnych opłat pod warunkiem, że powyższe uwagi zostaną 
// zachowane we wszystkich kopiach. Przyznaje się także prawo do modyfikacji kodu
// i dystrybucji zmodyfikowanego kodu pod warunkiem zachowania powyższych uwag
// oraz dołączenia informacji mówiącej o modyfikacji kodu.
//
// 
// ImportAddressPage.cpp : plik implementacji
//

#include "stdafx.h"
#include "AssemblyDoc.h"
#include "AssemblyView.h"
#include "ImportAddressPage.h"


// Okno dialogowe CImportAddressPage

IMPLEMENT_DYNAMIC(CImportAddressPage, CPropertyPage)
CImportAddressPage::CImportAddressPage()
	: CPropertyPage(CImportAddressPage::IDD)
{
}

CImportAddressPage::~CImportAddressPage()
{
}

void CImportAddressPage::DoDataExchange(CDataExchange* pDX)
{
	CPropertyPage::DoDataExchange(pDX);
}

BEGIN_MESSAGE_MAP(CImportAddressPage, CPropertyPage)
END_MESSAGE_MAP()

// Procedury obsługi wiadomości CImportAddressPage
BOOL CImportAddressPage::OnInitDialog()
{
	CPropertyPage::OnInitDialog();

	// Wypełnienie danymi
	CPropertySheet *pPropertySheet = STATIC_DOWNCAST(CPropertySheet, GetParent());
	CAssemblyView* pView = STATIC_DOWNCAST(CAssemblyView, pPropertySheet->GetParent());
	CAssemblyDoc* pDoc = pView->GetDocument();
	PBYTE pAssembly = pDoc->FileData();
	PIMAGE_DOS_HEADER dosHeader = (PIMAGE_DOS_HEADER)pAssembly;
    if ( dosHeader->e_magic == IMAGE_DOS_SIGNATURE )
    {
		PIMAGE_NT_HEADERS pNTHeader;
		PIMAGE_NT_HEADERS64 pNTHeader64;

		// Utworzenie wskaźników do 32- i 64-bitowej wersji nagłówka.
		pNTHeader = MakePtr( PIMAGE_NT_HEADERS,
			                 dosHeader,
							 dosHeader->e_lfanew );

		pNTHeader64 = (PIMAGE_NT_HEADERS64)pNTHeader;

		// Najpierw weryfikacja, czy pole e_lfanew przekazało właściwy wskaźnik,
		// a następnie weryfikacja sygnatury PE.
		if ( IsBadReadPtr( pNTHeader, sizeof(pNTHeader->Signature) ) )
		{
			ATLTRACE(L"To nie jest plik typu Portable Executable (PE) EXE\n");
			return FALSE;
		}

		if ( pNTHeader->Signature != IMAGE_NT_SIGNATURE )
		{
			ATLTRACE(L"To nie jest plik typu Portable Executable (PE) EXE\n");
			return FALSE;
		}

		bool bIs64Bit = ( pNTHeader->OptionalHeader.Magic == IMAGE_NT_OPTIONAL_HDR64_MAGIC );
		if(bIs64Bit)
		{
			DumpIATHeader( pAssembly, pNTHeader64 );
		}
		else
		{
			DumpIATHeader( pAssembly, pNTHeader );
		}

    }

	return TRUE;  // zwrócenie TRUE, chyba że ognisko ustawiono na element sterujący
}

template <class T> void CImportAddressPage::DumpIATHeader( PBYTE pImageBase, T* pNTHeader )	// T = PIMAGE_NT_HEADERS
{
	// IAT RVA
    DWORD IATHdrRVA;

    IATHdrRVA = GetImgDirEntryRVA(pNTHeader, IMAGE_DIRECTORY_ENTRY_IMPORT );
    if ( !IATHdrRVA )
        return;
	PIMAGE_IMPORT_DESCRIPTOR pIAT = (PIMAGE_IMPORT_DESCRIPTOR)GetPtrFromRVA( IATHdrRVA, pNTHeader, pImageBase );
	CEdit* pText;
	TCHAR cBuffer[128];

	pText = (CEdit*)GetDlgItem(IDC_IATFIRSTTHUNK);
	wsprintf(cBuffer, L"0x%08X", 
					pIAT->OriginalFirstThunk);
	pText->SetWindowText(cBuffer);

	LPDWORD pNameRVA = (LPDWORD)GetPtrFromRVA( pIAT->OriginalFirstThunk, pNTHeader, pImageBase );
	pText = (CEdit*)GetDlgItem(IDC_IATFIRSTTHUNKRVA);
	wsprintf(cBuffer, L"0x%08X", *pNameRVA);
	pText->SetWindowText(cBuffer);

	PIMAGE_IMPORT_BY_NAME pIATName = (PIMAGE_IMPORT_BY_NAME)GetPtrFromRVA( *pNameRVA, pNTHeader, pImageBase );
	pText = (CEdit*)GetDlgItem(IDC_IATFIRSTTHUNKNAME);
	mbstowcs(cBuffer, (LPCSTR)pIATName->Name, strlen((LPCSTR)pIATName->Name) + 1);
	pText->SetWindowText(cBuffer);

	pText = (CEdit*)GetDlgItem(IDC_IATTIMESTAMP);
	wsprintf(cBuffer, L"0x%08X", 
					pIAT->TimeDateStamp);
	pText->SetWindowText(cBuffer);

	pText = (CEdit*)GetDlgItem(IDC_IATFORWARDER);
	wsprintf(cBuffer, L"0x%08X", 
					pIAT->ForwarderChain);
	pText->SetWindowText(cBuffer);

	pText = (CEdit*)GetDlgItem(IDC_IATNAMERVA);
	wsprintf(cBuffer, L"0x%08X", 
					pIAT->Name);
	pText->SetWindowText(cBuffer);

	LPCSTR pName = (LPCSTR)GetPtrFromRVA( pIAT->Name, pNTHeader, pImageBase );
	pText = (CEdit*)GetDlgItem(IDC_IATNAME);
	mbstowcs(cBuffer, (LPCSTR)pName, strlen(pName) + 1);
	pText->SetWindowText(cBuffer);

	pText = (CEdit*)GetDlgItem(IDC_IATTHUNK);
	wsprintf(cBuffer, L"0x%08X", 
					pIAT->FirstThunk);
	pText->SetWindowText(cBuffer);

	pNameRVA = (LPDWORD)GetPtrFromRVA( pIAT->FirstThunk, pNTHeader, pImageBase );
	pText = (CEdit*)GetDlgItem(IDC_IATTHUNKRVA);
	wsprintf(cBuffer, L"0x%08X", *pNameRVA);
	pText->SetWindowText(cBuffer);

	pIATName = (PIMAGE_IMPORT_BY_NAME)GetPtrFromRVA( *pNameRVA, pNTHeader, pImageBase );
	pText = (CEdit*)GetDlgItem(IDC_IATTHUNKNAME);
	mbstowcs(cBuffer, (LPCSTR)pIATName->Name, strlen((LPCSTR)pIATName->Name) + 1);
	pText->SetWindowText(cBuffer);

	pIAT++;

	ASSERT(pIAT->Characteristics == 0);
}
