You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
193 lines
7.2 KiB
193 lines
7.2 KiB
/*
|
|
**++
|
|
**
|
|
** Copyright (c) 2002 Microsoft Corporation
|
|
**
|
|
**
|
|
** Module Name:
|
|
**
|
|
** swriter.h
|
|
**
|
|
**
|
|
** Abstract:
|
|
**
|
|
** Test program to to register a Writer with various properties
|
|
**
|
|
** Author:
|
|
**
|
|
** Reuven Lax [reuvenl] 04-June-2002
|
|
**
|
|
**
|
|
**
|
|
** Revision History:
|
|
**
|
|
**--
|
|
*/
|
|
|
|
#ifndef _SWRITER_H_
|
|
#define _SWRITER_H_
|
|
|
|
///////////////////////////////////////////////////////////////////////////////
|
|
// Includes
|
|
|
|
#include <vector>
|
|
#include <stack>
|
|
#include <functional>
|
|
#include <string>
|
|
#include "writerconfig.h"
|
|
#include "utility.h"
|
|
|
|
///////////////////////////////////////////////////////////////////////////////
|
|
// Declarations and Definitions
|
|
|
|
// {5AFFB034-969F-4919-8875-88F830D0EF89}
|
|
static const VSS_ID TestWriterId =
|
|
{ 0x5affb034, 0x969f, 0x4919, { 0x88, 0x75, 0x88, 0xf8, 0x30, 0xd0, 0xef, 0x89 } };
|
|
|
|
static const wchar_t* const TestWriterName = L"TestVssWriter";
|
|
|
|
using std::vector;
|
|
|
|
///////////////////////////////////////////////////////////////////////////////
|
|
// TestWriter class
|
|
|
|
class TestWriter : public CVssWriter {
|
|
private:
|
|
// member variables
|
|
vector<Component> m_selectedComponents;
|
|
vector<Component> m_selectedRestoreComponents;
|
|
vector<wstring> m_toDelete;
|
|
std::stack<wstring> m_directoriesToRemove;
|
|
long m_failures[Utility::NumEvents];
|
|
|
|
// closure to encapsulate calls to verifyFileAtLocation and record error messages
|
|
class VerifyFileAtLocation : public std::binary_function<const TargetedFile, const File, void> {
|
|
private:
|
|
const vector<File>& m_excluded;
|
|
bool m_verifyAlternateLocation;
|
|
mutable IVssComponent* m_pComponent; // necessary due to bug in STL
|
|
|
|
wstring verifyFileAtLocation(const File& file, const TargetedFile& location) const;
|
|
bool verifyAlternateLocation(const TargetedFile& writerAlt) const;
|
|
void saveErrorMessage(const wstring& message) const;
|
|
public:
|
|
VerifyFileAtLocation(const vector<File>& excludeFiles, IVssComponent* pComponent,
|
|
bool verifyAlternateLocation) :
|
|
m_excluded(excludeFiles), m_pComponent(pComponent),
|
|
m_verifyAlternateLocation(verifyAlternateLocation)
|
|
{}
|
|
|
|
// The function operator. Verifies the file, and records any error message
|
|
void operator()(const TargetedFile location, const File file) const {
|
|
saveErrorMessage(verifyFileAtLocation(file, location));
|
|
}
|
|
};
|
|
|
|
// static helper functions
|
|
|
|
// filter out elements in a source container that match a specific condition. Place these elements
|
|
// into a target container.
|
|
template <class SourceIterator, class TargetIterator, class Condition>
|
|
static void buildContainer_if(SourceIterator begin, SourceIterator end, TargetIterator output, Condition cond) {
|
|
SourceIterator current = std::find_if(begin, end, cond);
|
|
while (current != end) {
|
|
*output++ = *current++;
|
|
current = std::find_if(current, end, cond);
|
|
}
|
|
}
|
|
|
|
|
|
// build a list of all files in this component and in all non-selectable subcomponents
|
|
template<class TargetIterator>
|
|
static void __cdecl buildComponentFiles(Component component, TargetIterator output) {
|
|
WriterConfiguration* config = WriterConfiguration::instance();
|
|
|
|
buildComponentFilesHelper(component, output);
|
|
|
|
// build a list of all subcomponents
|
|
vector<Component> subcomponents;
|
|
buildContainer_if(config->components().begin(),
|
|
config->components().end(),
|
|
std::back_inserter(subcomponents),
|
|
std::bind2nd(std::ptr_fun(isSubcomponent), component));
|
|
|
|
// add all files in all non-selectable subcomponents to the output
|
|
std::pointer_to_binary_function<Component, std::back_insert_iterator<vector<TargetedFile> >, void>
|
|
ptrFun(buildComponentFilesHelper);
|
|
std::for_each(subcomponents.begin(),
|
|
subcomponents.end(),
|
|
std::bind2nd(ptrFun, output));
|
|
}
|
|
|
|
template<class TargetIterator>
|
|
static void __cdecl buildComponentFilesHelper(Component component, TargetIterator output) {
|
|
// add all the files in the current component
|
|
Component::ComponentFileList::iterator currentCompFile = component.m_files.begin();
|
|
while (currentCompFile != component.m_files.end())
|
|
*output++ = *currentCompFile++;
|
|
}
|
|
|
|
static bool __cdecl isSubcomponent(ComponentBase sub, ComponentBase super);
|
|
static bool __cdecl isSupercomponent(ComponentBase super, ComponentBase sub) {
|
|
return isSubcomponent(sub, super);
|
|
}
|
|
|
|
// return whether a component is selectable for backup
|
|
static bool __cdecl isComponentSelectable(Component component) {
|
|
return component.m_selectable;
|
|
}
|
|
|
|
static bool __cdecl addableComponent(Component toAdd);
|
|
|
|
// Returns whether a filespec is a wildcard or an exact filespec.
|
|
static bool isExact(const wstring& file) { return file.find_first_of(L"*?") == wstring::npos; }
|
|
|
|
static bool __cdecl targetMatches(File target, File file);
|
|
static bool wildcardMatches(const wstring& first, const wstring& second);
|
|
|
|
// non-static helper functions
|
|
void enterEvent(Utility::Events event);
|
|
void addComponent(const Component& component, IVssCreateWriterMetadata* pMetadata);
|
|
void spitFiles(const TargetedFile& file);
|
|
wstring getName(IVssComponent* pComponent);
|
|
wstring getPath(IVssComponent* pComponent);
|
|
void writeBackupMetadata(IVssComponent* pComponent);
|
|
bool verifyBackupMetadata(IVssComponent* pComponent);
|
|
void writeRestoreMetadata(IVssComponent* pComponent);
|
|
bool verifyRestoreMetadata(IVssComponent* pComponent);
|
|
bool checkPathAffected(const TargetedFile& file);
|
|
void cleanupFiles();
|
|
void updateNewTargets(IVssComponent* pComponent, Component& writerComponent);
|
|
void verifyFilesRestored(IVssComponent* pComponent, const Component& writerComponent);
|
|
|
|
// returns the private metadata string that the writer stores in the document
|
|
wstring metadata(IVssComponent* pComponent, const wstring& suffix) {
|
|
return getPath(pComponent) + L"\\" + getName(pComponent) + suffix;
|
|
}
|
|
|
|
bool inSequence(Utility::Events event) {
|
|
return event != Utility::Identify && event != Utility::BackupComplete &&
|
|
event != Utility::BackupShutdown;
|
|
}
|
|
public:
|
|
TestWriter() { memset(m_failures, 0, sizeof(m_failures)); }
|
|
virtual ~TestWriter() { Uninitialize(); }
|
|
|
|
HRESULT STDMETHODCALLTYPE Initialize();
|
|
HRESULT STDMETHODCALLTYPE Uninitialize() { return Unsubscribe(); }
|
|
bool STDMETHODCALLTYPE OnIdentify(IN IVssCreateWriterMetadata *pMetadata);
|
|
bool STDMETHODCALLTYPE OnPrepareBackup(IN IVssWriterComponents *pComponents);
|
|
bool STDMETHODCALLTYPE OnPrepareSnapshot();
|
|
bool STDMETHODCALLTYPE OnFreeze();
|
|
bool STDMETHODCALLTYPE OnThaw();
|
|
bool STDMETHODCALLTYPE OnPostSnapshot(IN IVssWriterComponents *pComponents);
|
|
bool STDMETHODCALLTYPE OnAbort();
|
|
bool STDMETHODCALLTYPE OnBackupComplete(IN IVssWriterComponents *pComponents);
|
|
bool STDMETHODCALLTYPE OnBackupShutdown(IN VSS_ID SnapshotSetId);
|
|
bool STDMETHODCALLTYPE OnPreRestore(IN IVssWriterComponents *pComponents);
|
|
bool STDMETHODCALLTYPE OnPostRestore(IN IVssWriterComponents *pComponents);
|
|
};
|
|
|
|
|
|
#endif
|
|
|