###############################################################################
+Project: "isapi_shib_gui"=.\isapi_shib_gui\isapi_shib_gui.dsp - Package Owner=<4>
+
+Package=<5>
+{{{
+}}}
+
+Package=<4>
+{{{
+}}}
+
+###############################################################################
+
Project: "mod_shire"=.\mod_shire\mod_shire.dsp - Package Owner=<4>
Package=<5>
Package=<5>
{{{
- begin source code control
- "$/NSAPI", WNAAAAAA
- ..\..\..\documents and settings\cantor.2.saidin\my documents\visual studio projects\nsapi
- end source code control
}}}
Package=<3>
--- /dev/null
+#include <string>
+#include <tchar.h>
+#define STR_PENDING_DELETION "(Pending Removal)"
+
+using namespace std;
+
+class Directive
+{
+public:
+
+ Directive() {
+ }
+
+ ~Directive() {
+ }
+
+ Directive(unsigned int which_directive) {
+ Init_Directive(which_directive);
+ }
+
+ string name;
+ unsigned short type;
+ string value;
+ string new_value;
+ string defined_in;
+ string description;
+ string bound_val[NUM_BOUND_VAL];
+ string MachineName;
+ unsigned int d_index;
+
+ bool Set_Path(string new_path)
+ {
+ if (new_path.length() && new_path.at(0) == '/') {
+ path = new_path;
+ } else {
+ path = "/";
+ path += new_path;
+ }
+ Get_Value();
+ return true;
+ }
+
+ bool WriteValue(string RegPath)
+ {
+ if (type == D_BOUND_INT || type == D_FREE_INT) {
+ return WriteRegInt(RegPath.c_str(), name.c_str(), new_value.c_str());
+ } else {
+ return WriteRegString(RegPath.c_str(), name.c_str(), new_value.c_str());
+ }
+ }
+
+ void Directive::Init_Directive(unsigned int w) {
+
+ if (w >= NUM_DIRECTIVES) {
+ return;
+ }
+ d_index = w;
+ name = directives[w].name;
+ type = directives[w].type;
+ value = directives[w].value;
+ defined_in = directives[w].defined_in;
+ description = directives[w].description;
+ for (int i=0;i<NUM_BOUND_VAL;i++) {
+ bound_val[i] = directives[w].bound_val[i];
+ }
+ }
+
+ void DeleteValue()
+ {
+ new_value = STR_PENDING_DELETION;
+ }
+
+ bool Directive::DeleteRegVal(string Key)
+ {
+ HKEY hKey;
+
+ if ((hKey=OpenKey(Key.c_str(),KEY_ALL_ACCESS))) {
+ if (RegDeleteValue(hKey,name.c_str()) == ERROR_SUCCESS) {
+ return true;
+ }
+ }
+ return false;
+ }
+
+private:
+
+ string path;
+
+ HKEY Directive::OpenKey(LPCTSTR szKey, REGSAM samDesired) {
+
+ HKEY hKey,rhKey;
+ _TCHAR localname[MAX_PATH];
+ DWORD lsize = MAX_PATH;
+
+ //Support for Remote Registries
+ GetComputerName(localname,&lsize);
+ if (!_tcsicmp(localname,MachineName.c_str())) {
+ rhKey = HKEY_LOCAL_MACHINE;
+ }else {
+ if (RegConnectRegistry(MachineName.c_str(),HKEY_LOCAL_MACHINE, &rhKey) != ERROR_SUCCESS) {
+ //MessageBox(hwndDlg,L"Error opening remote registry. Values displayed may not be accurate.",L"Error",MB_ICONERROR);
+ }
+ }
+
+ if (samDesired == KEY_READ) {
+ // Open existing key.
+ if( RegOpenKeyEx(rhKey,
+ szKey,
+ 0,
+ samDesired,
+ &hKey) != ERROR_SUCCESS)
+ {
+ return NULL ;
+ }
+
+ } else {
+ // Create and open key and subkey.
+ if( RegCreateKeyEx(rhKey,
+ szKey,
+ 0, NULL, REG_OPTION_NON_VOLATILE,
+ samDesired, NULL,
+ &hKey, NULL) != ERROR_SUCCESS)
+ {
+ return NULL ;
+ }
+ }
+
+ return hKey;
+
+ }
+
+ void Directive::ReadValAsString(string key, LPCTSTR defined_in_val) {
+ HKEY hKey;
+ char RegBuff[MAX_REG_BUFF];
+ long debug;
+ DWORD dwRead=MAX_REG_BUFF*sizeof(char);
+
+ if (hKey = OpenKey(key.c_str(),KEY_READ)) {
+ if ((debug = RegQueryValueEx (hKey,name.c_str(), NULL, NULL, (LPBYTE)RegBuff, &dwRead)) == ERROR_SUCCESS) {
+ if (type == D_FREE_INT || type == D_BOUND_INT) {
+ char tmpw[22];
+ value = itoa(*(DWORD *)RegBuff,tmpw,10);
+ } else {
+ value = RegBuff;
+ }
+ defined_in = defined_in_val;
+ }
+ RegCloseKey (hKey);
+ }
+ }
+
+ bool Directive::WriteRegInt(const _TCHAR* szKey,
+ const _TCHAR* szValueName,
+ const _TCHAR* szValue)
+ {
+ HKEY hKey;
+ DWORD value;
+
+ if (!(hKey=OpenKey(szKey,KEY_ALL_ACCESS)))
+ return FALSE;
+
+ // Set the Value.
+ if (szValue != NULL)
+ {
+ value = _ttoi(szValue);
+ RegSetValueEx(hKey, szValueName, 0, REG_DWORD,
+ (BYTE *)&value,
+ sizeof(DWORD)) ;
+ }
+
+ RegCloseKey(hKey) ;
+ return TRUE ;
+ }
+
+
+ bool Directive::WriteRegString(const _TCHAR* szKey,
+ const _TCHAR* szValueName,
+ const _TCHAR* szValue)
+ {
+ HKEY hKey;
+
+ if (!(hKey=OpenKey(szKey,KEY_ALL_ACCESS)))
+ return FALSE;
+
+ // Set the Value.
+ if (szValue != NULL)
+ {
+ RegSetValueEx(hKey, szValueName, 0, REG_SZ,
+ (BYTE *)szValue,
+ ((DWORD)_tcslen(szValue)+1)*sizeof(_TCHAR)) ;
+ }
+
+ RegCloseKey(hKey);
+ return TRUE ;
+ }
+
+ void Directive::Get_Value() {
+
+ string key, node, defined_in_val;
+ size_t pos = 0;
+ size_t opos = 0;
+ char done = 0;
+
+ value = directives[d_index].value;
+ defined_in = directives[d_index].defined_in;
+
+ key = SHIB_DEFAULT_WEB_KEY;
+
+ do {
+
+ pos = path.find('/',opos); // while we still have a '/' left to deal with
+
+ if (pos != string::npos) {
+ node = path.substr(opos,pos-opos);
+ }
+ else {
+ node = path.substr(opos);
+ done = 1;
+ }
+ if (defined_in_val[defined_in_val.length()-1] != '/') {
+ defined_in_val += "/";
+ key += "\\";
+ }
+
+ defined_in_val += node;
+ key += node;
+
+ ReadValAsString(key,defined_in_val.c_str());
+ opos = pos+1;
+
+ } while (!done);
+ }
+};
--- /dev/null
+#define SHIB_REG_KEY "Software\\Internet2\\Shibboleth"
+#define SHIB_DEFAULT_WEB_KEY "Software\\Internet 2\\Shibboleth\\Webs\\default"
+#define D_FREE_STRING 0
+#define D_FREE_INT 1
+#define D_BOUND_INT 2
+#define D_BOUND_STRING 3
+#define MAX_REG_BUFF 4096 // Using a fixed size saves a registy lookup and malloc
+#define MAX_DIRECTIVE_STRING 256 // Set to lagest size of default strings below
+
+#define NUM_DIRECTIVES 2 // Set to number of directives below
+#define NUM_BOUND_VAL 2 // Set to maximum number of bound values
+
+struct directives_t {
+ char name[MAX_DIRECTIVE_STRING];
+ unsigned short type;
+ char value[MAX_DIRECTIVE_STRING];
+ char description[MAX_DIRECTIVE_STRING];
+ char defined_in[MAX_DIRECTIVE_STRING];
+ char bound_val[NUM_BOUND_VAL][MAX_DIRECTIVE_STRING];
+};
+
+const directives_t directives[] = {
+ {
+# define DIRECTIVE_AUTHTYPE 0 // defines make code more readable than enum
+ "AuthType", // name
+ D_FREE_STRING, // type
+ "None", // default value. Case insensitive.
+ "Use Shibboleth to enable Shibboleth. Any other value disables Shibboleth.\nIf no value specified," \
+ " the MustContain string will be searched for in the target URL.", // description
+ "(Program Default)", // default value for defined_in
+ "", // possible bound value
+ "" // possible bound value
+ },
+ {
+# define DIRECTIVE_SSL_ONLY 1 // Example only, not implemented in filter
+ "ShibSSLOnly",
+ D_BOUND_STRING,
+ "Off",
+ "Controls whether Shibboleth will reject non-SSL requests for resources from clients.",
+ "(Program Default)",
+ "On",
+ "Off"
+
+ }
+};
\ No newline at end of file
# PROP Ignore_Export_Lib 0
# PROP Target_Dir ""
# ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "ISAPI_SHIB_EXPORTS" /YX /FD /c
-# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I ".." /I "..\..\..\opensaml\c" /I "..\oncrpc" /I "." /D "NDEBUG" /D "WIN32" /D "_WINDOWS" /D "_MBCS" /YX /FD /c
+# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I ".." /I "..\..\..\opensaml\c" /I "..\oncrpc" /I "." /D "NDEBUG" /D "WIN32" /D "_WINDOWS" /D "_MBCS" /FR /YX /FD /c
# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32
# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32
# ADD BASE RSC /l 0x409 /d "NDEBUG"
# ADD BSC32 /nologo
LINK32=link.exe
# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept
-# ADD LINK32 log4cppD.lib xerces-c_2D.lib xsec_1D.lib advapi32.lib kernel32.lib saml_4D.lib /nologo /dll /debug /machine:I386 /pdbtype:sept /libpath:"C:\debug\log4cpp\lib" /libpath:"C:\debug\xerces-c\lib" /libpath:"..\..\..\opensaml\c\saml\Debug" /export:GetExtensionVersion /export:GetFilterVersion /export:TerminateExtension /export:TerminateFilter /export:HttpFilterProc /export:HttpExtensionProc
+# ADD LINK32 log4cppD.lib xerces-c_2D.lib xsec_1D.lib advapi32.lib kernel32.lib saml_4D.lib /nologo /dll /debug /machine:I386 /pdbtype:sept /libpath:"G:\src\log4cpp-0.3.4b\msvc6\log4cppDLL\Debug" /libpath:"C:\debug\xerces-c\lib" /libpath:"..\..\..\opensaml\c\saml\Debug" /export:GetExtensionVersion /export:GetFilterVersion /export:TerminateExtension /export:TerminateFilter /export:HttpFilterProc /export:HttpExtensionProc
# SUBTRACT LINK32 /pdb:none
!ENDIF
# End Source File
# Begin Source File
+SOURCE=.\directive_class.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\directives.h
+# End Source File
+# Begin Source File
+
SOURCE=.\isapi_shib.cpp
# End Source File
# End Target
--- /dev/null
+// {4DC08CD0-7141-4715-A1E6-A11E5FF231D6}
+DEFINE_GUID(CLSID_Shib_PropSheet,
+0x4dc08cd0, 0x7141, 0x4715, 0xa1, 0xe6, 0xa1, 0x1e, 0x5f, 0xf2, 0x31, 0xd6);
+
+#define PBC_EXTENDER_NODES \
+ {{PropertySheetExtension,\
+ {0xa841b6c9, 0x7577, 0x11d0, { 0xbb, 0x1f, 0x0, 0xa0, 0xc9, 0x22, 0xe7, 0x9c}},\
+ {0x4dc08cd0, 0x7141, 0x4715, { 0xa1, 0xe6, 0xa1, 0x1e, 0x5f, 0xf2, 0x31, 0xd6}},\
+ _T("Shibboleth Directives")},\
+\
+ {PropertySheetExtension,\
+ {0xa841b6c8, 0x7577, 0x11d0, { 0xbb, 0x1f, 0x0, 0xa0, 0xc9, 0x22, 0xe7, 0x9c}},\
+ {0x4dc08cd0, 0x7141, 0x4715, { 0xa1, 0xe6, 0xa1, 0x1e, 0x5f, 0xf2, 0x31, 0xd6}},\
+ _T("Shibboleth Directives")},\
+\
+ {PropertySheetExtension,\
+ {0xa841b6c7, 0x7577, 0x11d0, { 0xbb, 0x1f, 0x0, 0xa0, 0xc9, 0x22, 0xe7, 0x9c}},\
+ {0x4dc08cd0, 0x7141, 0x4715, { 0xa1, 0xe6, 0xa1, 0x1e, 0x5f, 0xf2, 0x31, 0xd6}},\
+ _T("Shibboleth Directives")},\
+\
+ {DummyExtension,\
+ NULL,\
+ NULL,\
+ NULL}}
\ No newline at end of file
--- /dev/null
+#include <windows.h>
+#include "Shib_PropSheet.h"
+#include <crtdbg.h>
+#include <string>
+#include <tchar.h>
+#include <strsafe.h>
+#include "resource.h"
+#include "globals.h"
+#include "atou.h"
+using namespace std;
+
+
+void Shib_PropSheet::ReplaceSlashes(string& buf)
+{
+ size_t p=0;
+
+ while ((p = buf.find('/',p)) != string::npos) {
+ buf.at(p) = '\\';
+ p++;
+ }
+}
+
+Shib_PropSheet::Shib_PropSheet() : m_cref(0)
+{
+ for (int i=0;i<NUM_DIRECTIVES;i++) {
+ directive[i].Init_Directive(i);
+ }
+
+ pwzService=NULL;
+ pwzParentPath=NULL;
+ pwzNode=NULL;
+ pwzMetaPath=NULL;
+ pwzMachineName=NULL;
+ pwzInstance=NULL;
+ pwzRegPath=NULL;
+ OBJECT_CREATED
+}
+
+
+Shib_PropSheet::~Shib_PropSheet()
+{
+ if ( pwzService )
+ ::LocalFree(pwzService);
+ if ( pwzParentPath )
+ ::LocalFree(pwzParentPath);
+ if ( pwzNode )
+ ::LocalFree(pwzNode);
+ if ( pwzMetaPath )
+ ::LocalFree(pwzMetaPath);
+ if ( pwzMachineName )
+ ::LocalFree(pwzMachineName);
+ if ( pwzInstance )
+ ::LocalFree(pwzInstance);
+ if ( pwzRegPath )
+ ::LocalFree(pwzRegPath);
+
+ OBJECT_DESTROYED
+}
+
+///////////////////////
+// IUnknown implementation
+///////////////////////
+
+STDMETHODIMP Shib_PropSheet::QueryInterface(REFIID riid, LPVOID *ppv)
+{
+ if (!ppv)
+ return E_FAIL;
+
+ *ppv = NULL;
+
+ if (IsEqualIID(riid, IID_IUnknown))
+ *ppv = static_cast<IExtendPropertySheet *>(this);
+ else if (IsEqualIID(riid, IID_IExtendPropertySheet))
+ *ppv = static_cast<IExtendPropertySheet *>(this);
+
+ if (*ppv)
+ {
+ reinterpret_cast<IUnknown *>(*ppv)->AddRef();
+ return S_OK;
+ }
+
+ return E_NOINTERFACE;
+}
+
+STDMETHODIMP_(ULONG) Shib_PropSheet::AddRef()
+{
+ return InterlockedIncrement((LONG *)&m_cref);
+}
+
+STDMETHODIMP_(ULONG) Shib_PropSheet::Release()
+{
+ if (InterlockedDecrement((LONG *)&m_cref) == 0)
+ {
+ // we need to decrement our object count in the DLL
+ delete this;
+ return 0;
+ }
+
+ return m_cref;
+}
+
+HRESULT Shib_PropSheet::ExtractData( IDataObject* piDataObject,
+ CLIPFORMAT cfClipFormat,
+ BYTE* pbData,
+ DWORD cbData )
+{
+ HRESULT hr = S_OK;
+
+ FORMATETC formatetc = {cfClipFormat, NULL, DVASPECT_CONTENT, -1, TYMED_HGLOBAL};
+ STGMEDIUM stgmedium = {TYMED_HGLOBAL, NULL};
+
+ stgmedium.hGlobal = ::GlobalAlloc(GPTR, cbData);
+ do
+ {
+ if (NULL == stgmedium.hGlobal)
+ {
+ hr = E_OUTOFMEMORY;
+ break;
+ }
+ hr = piDataObject->GetDataHere( &formatetc, &stgmedium );
+ if ( FAILED(hr) )
+ {
+ break;
+ }
+
+ BYTE* pbNewData = reinterpret_cast<BYTE*>(stgmedium.hGlobal);
+ if (NULL == pbNewData)
+ {
+ hr = E_UNEXPECTED;
+ break;
+ }
+ ::memcpy( pbData, pbNewData, cbData );
+ } while (FALSE);
+
+ if (NULL != stgmedium.hGlobal)
+ {
+ ::GlobalFree(stgmedium.hGlobal);
+ }
+ return hr;
+}
+
+
+void Shib_PropSheet::PopulateComboBox()
+{
+
+ for (int i = 0; i < NUM_DIRECTIVES; i++)
+ {
+ LRESULT index = SendMessage(hProps, CB_ADDSTRING, 0, (LPARAM) (LPWSTR) directive[i].name.c_str());
+ LRESULT debug = SendMessage(hProps, CB_SETITEMDATA, (WPARAM)index, (LPARAM)i );
+ }
+
+ LRESULT debug = SendMessage(hProps, CB_SETCURSEL, 0, 0); // wparam = index, lparam = not used
+
+}
+
+BOOL Shib_PropSheet::UpdateNewValue() {
+ _TCHAR value[MAX_REG_BUFF];
+
+ DWORD index = SendMessage(hProps, CB_GETCURSEL, 0,0);
+ UINT i = SendMessage(hProps, CB_GETITEMDATA, (WPARAM)index, 0 );
+
+ if (directive[i].type == D_BOUND_INT || directive[i].type == D_BOUND_STRING) {
+ index = SendMessage(hValueBox, CB_GETCURSEL, 0,0);
+ if (index == CB_ERR) { return FALSE; }
+ LRESULT debug = SendMessage(hValueBox, CB_GETLBTEXT, (WPARAM)index, (LPARAM)value );
+ } else {
+ LRESULT debug = SendMessage(hValueEdit, WM_GETTEXT, (WPARAM)MAX_REG_BUFF, (LPARAM)value );
+ }
+
+ directive[i].new_value = value;
+ if (!_tcsicmp(directive[i].value.c_str(),value)) {
+ return FALSE;
+ } else {
+ return TRUE;
+ }
+}
+
+void Shib_PropSheet::GetHandles() {
+ hValueBox = GetDlgItem(hwndDlg, IDC_ValueBox);
+ hValueEdit = GetDlgItem(hwndDlg, IDC_ValueEdit);
+ hInheritedFrom = GetDlgItem(hwndDlg, IDC_InheritedFrom);
+ hMoreInfo = GetDlgItem(hwndDlg, IDC_MoreInfo);
+ hProps = GetDlgItem(hwndDlg, IDC_PROPS);
+ hDelete = GetDlgItem(hwndDlg, IDC_Delete);
+}
+
+void Shib_PropSheet::PopulatePage() {
+
+ DWORD index = SendMessage(hProps, CB_GETCURSEL, 0,0);
+ LRESULT i = SendMessage(hProps, CB_GETITEMDATA, (WPARAM)index, 0 );
+
+ Set_Delete_Button(i);
+
+ if (directive[i].type == D_BOUND_INT || directive[i].type == D_BOUND_STRING) {
+ ShowWindow(hValueEdit,SW_HIDE);
+ ShowWindow(hValueBox,SW_SHOW);
+ SendMessage(hValueBox,CB_RESETCONTENT,0,0);
+ for(int vi=0;vi < NUM_BOUND_VAL;vi++) {
+ if (directive[i].bound_val[vi].length()) {
+ LRESULT index = SendMessage(hValueBox, CB_INSERTSTRING, -1, (LPARAM) (LPWSTR) directive[i].bound_val[vi].c_str());
+ }
+ }
+
+ SendMessage(hValueBox, WM_SETTEXT, 0, (LPARAM) directive[i].new_value.c_str());
+ } else {
+ ShowWindow(hValueEdit,SW_SHOW);
+ ShowWindow(hValueBox,SW_HIDE);
+ SendMessage(hValueEdit, WM_SETTEXT, 0, (LPARAM) directive[i].new_value.c_str());
+ }
+
+ SendMessage(hMoreInfo, WM_SETTEXT, 0, (LPARAM) directive[i].description.c_str());
+ SendMessage(hInheritedFrom, WM_SETTEXT, 0, (LPARAM) directive[i].defined_in.c_str());
+
+}
+
+void Shib_PropSheet::DeleteValue() {
+
+ DWORD index = SendMessage(hProps, CB_GETCURSEL, 0,0);
+ LRESULT i = SendMessage(hProps, CB_GETITEMDATA, (WPARAM)index, 0 );
+
+ directive[i].DeleteValue();
+
+}
+
+void Shib_PropSheet::SetupPropSheet() {
+
+ GetHandles();
+ ReadCurrentValues();
+ PopulateComboBox();
+ PopulatePage();
+
+}
+
+BOOL CALLBACK Shib_PropSheet::DialogProc(
+ HWND hwndDlg, // handle to dialog box
+ UINT uMsg, // message
+ WPARAM wParam, // first message parameter
+ LPARAM lParam // second message parameter
+ )
+{
+
+ if (uMsg == WM_INITDIALOG) {
+ Shib_PropSheet *pThis=reinterpret_cast<Shib_PropSheet *>(reinterpret_cast<PROPSHEETPAGE *>(lParam)->lParam);
+ pThis->hwndDlg=hwndDlg; //store property page handle in class
+ SetWindowLongPtr(hwndDlg,DWLP_USER,(LONG_PTR)pThis); //store class pointer in property page
+ pThis->SetupPropSheet();
+ } else {
+ Shib_PropSheet *pThis = reinterpret_cast<Shib_PropSheet *>(reinterpret_cast<PROPSHEETPAGE *>(GetWindowLongPtr(hwndDlg,DWLP_USER))); //retrieve class pointer from property page
+ switch (uMsg) {
+ case WM_COMMAND:
+ if (HIWORD(wParam) == EN_CHANGE || HIWORD(wParam) == CBN_SELCHANGE) {
+ if ((HWND)lParam == GetDlgItem(hwndDlg,IDC_PROPS)) { //if the user changes directives
+ pThis->PopulatePage(); //redraw page
+ } else {
+ if (pThis->UpdateNewValue()) {
+ //if anything else changes, light the apply button
+ SendMessage(GetParent(hwndDlg), PSM_CHANGED, (WPARAM)hwndDlg, 0);
+ }
+ }
+ }
+ if (wParam == IDC_Delete) {
+ pThis->DeleteValue();
+ pThis->PopulatePage();
+ SendMessage(GetParent(hwndDlg), PSM_CHANGED, (WPARAM)hwndDlg, 0); //light apply
+ } else if (wParam == IDC_Refresh) {
+ pThis->ReadCurrentValues(); //refresh values
+ pThis->PopulatePage(); //refresh page
+ }
+ break;
+
+ case WM_DESTROY:
+ break;
+
+ case WM_NOTIFY:
+ switch (((NMHDR *) lParam)->code) {
+ case PSN_APPLY:
+ pThis->UpdateNewValue(); //collect last-minute changes
+ pThis->WriteValues(); //write new values
+ pThis->ReadCurrentValues(); //refresh values
+ pThis->PopulatePage(); //refresh page
+ return PSNRET_NOERROR;
+ }
+ break;
+ }
+ }
+ return FALSE; //Seems to not fall through to parent page if you use DefWindowProc
+ //return DefWindowProc(hwndDlg, uMsg, wParam, lParam);
+}
+
+///////////////////////////////
+// Interface IExtendPropertySheet
+///////////////////////////////
+HRESULT Shib_PropSheet::CreatePropertyPages(
+ /* [in] */ LPPROPERTYSHEETCALLBACK lpProvider,
+ /* [in] */ LONG_PTR handle,
+ /* [in] */ LPDATAOBJECT lpIDataObject)
+{
+ PROPSHEETPAGE psp;
+ HPROPSHEETPAGE hPage = NULL;
+
+ // cache this handle so we can call MMCPropertyChangeNotify
+ m_ppHandle = handle;
+
+ UINT s_cfInstance =
+ RegisterClipboardFormat(_T("ISM_SNAPIN_INSTANCE"));
+ UINT s_cfMachineName =
+ RegisterClipboardFormat(_T("ISM_SNAPIN_MACHINE_NAME"));
+ UINT s_cfMetaPath =
+ RegisterClipboardFormat(_T("ISM_SNAPIN_META_PATH"));
+ UINT s_cfNode =
+ RegisterClipboardFormat(_T("ISM_SNAPIN_NODE"));
+ UINT s_cfParentPath =
+ RegisterClipboardFormat(_T("ISM_SNAPIN_PARENT_PATH"));
+ UINT s_cfService =
+ RegisterClipboardFormat(_T("ISM_SNAPIN_SERVICE"));
+
+ if ( !lpProvider || !lpIDataObject )
+ return E_POINTER;
+
+ HRESULT hr = S_OK;
+
+ DWORD dwLength = MAX_PATH * sizeof(_TCHAR);
+ DWORD dwWLength = MAX_PATH * sizeof(wchar_t);
+
+ LPWSTR pwztInstance = reinterpret_cast<LPWSTR>(::LocalAlloc(LPTR, dwWLength));
+ LPWSTR pwztMachineName = reinterpret_cast<LPWSTR>(::LocalAlloc(LPTR, dwWLength));
+ LPWSTR pwztMetaPath = reinterpret_cast<LPWSTR>(::LocalAlloc(LPTR, dwWLength));
+ LPWSTR pwztNode = reinterpret_cast<LPWSTR>(::LocalAlloc(LPTR, dwWLength));
+ LPWSTR pwztParentPath = reinterpret_cast<LPWSTR>(::LocalAlloc(LPTR, dwWLength));
+ LPWSTR pwztService = reinterpret_cast<LPWSTR>(::LocalAlloc(LPTR, dwWLength));
+
+ if ( pwztInstance )
+ Shib_PropSheet::ExtractWString(lpIDataObject, s_cfInstance, pwztInstance, dwLength);
+ if ( pwztMachineName )
+ Shib_PropSheet::ExtractWString(lpIDataObject, s_cfMachineName, pwztMachineName, dwLength);
+ if ( pwztMetaPath )
+ Shib_PropSheet::ExtractWString(lpIDataObject, s_cfMetaPath, pwztMetaPath, dwLength);
+ if ( pwztNode )
+ Shib_PropSheet::ExtractWString(lpIDataObject, s_cfNode, pwztNode, dwLength);
+ if ( pwztParentPath )
+ Shib_PropSheet::ExtractWString(lpIDataObject, s_cfParentPath, pwztParentPath, dwLength);
+ if ( pwztService )
+ Shib_PropSheet::ExtractWString(lpIDataObject, s_cfService, pwztService, dwLength);
+
+ /* IIS only supports Unicode clipboard formats */
+#ifdef _UNICODE
+ pwzInstance = pwztInstance;
+ pwzMachineName = pwztMachineName;
+ pwzMetaPath = pwztMetaPath;
+ pwzNode = pwztNode;
+ pwzParentPath = pwztParentPath;
+ pwzService = pwztService;
+#else
+ pwzInstance = reinterpret_cast<LPSTR>(::LocalAlloc(LPTR, dwLength));
+ pwzMachineName = reinterpret_cast<LPSTR>(::LocalAlloc(LPTR, dwLength));
+ pwzMetaPath = reinterpret_cast<LPSTR>(::LocalAlloc(LPTR, dwLength));
+ pwzNode = reinterpret_cast<LPSTR>(::LocalAlloc(LPTR, dwLength));
+ pwzParentPath = reinterpret_cast<LPSTR>(::LocalAlloc(LPTR, dwLength));
+ pwzService = reinterpret_cast<LPSTR>(::LocalAlloc(LPTR, dwLength));
+
+ UnicodeToAnsi(pwztInstance,&pwzInstance);
+ UnicodeToAnsi(pwztMachineName,&pwzMachineName);
+ UnicodeToAnsi(pwztMetaPath,&pwzMetaPath);
+ UnicodeToAnsi(pwztNode,&pwzNode);
+ UnicodeToAnsi(pwztParentPath,&pwzParentPath);
+ UnicodeToAnsi(pwztService,&pwzService);
+
+ if ( pwztService )
+ ::LocalFree(pwztService);
+ if ( pwztParentPath )
+ ::LocalFree(pwztParentPath);
+ if ( pwztNode )
+ ::LocalFree(pwztNode);
+ if ( pwztMetaPath )
+ ::LocalFree(pwztMetaPath);
+ if ( pwztMachineName )
+ ::LocalFree(pwztMachineName);
+ if ( pwztInstance )
+ ::LocalFree(pwztInstance);
+
+#endif
+
+ for (int i=0;i<NUM_DIRECTIVES;i++) {
+ directive[i].MachineName = pwzMachineName;
+ }
+ pwzRegPath = reinterpret_cast<LPTSTR>(::LocalAlloc(LPTR, (dwLength*2)+1));
+
+ LPTSTR ppath = _tcschr(pwzParentPath,_T('/'));
+ if (ppath) {
+ StringCbCopy(pwzRegPath, MAX_PATH*2 ,ppath+1);
+ StringCbCat (pwzRegPath, MAX_PATH*2 ,_T("/"));
+ } else {
+ pwzRegPath[0] = 0;
+ }
+ StringCbCat(pwzRegPath, MAX_PATH*2 ,pwzNode);
+
+ psp.dwSize = sizeof(PROPSHEETPAGE);
+ psp.dwFlags = PSP_DEFAULT | PSP_USETITLE | PSP_USEICONID;
+ psp.hInstance = g_hinst;
+ psp.pszTemplate = MAKEINTRESOURCE(IDD_PROPPAGE);
+ psp.pfnDlgProc = DialogProc;
+ psp.lParam = reinterpret_cast<LPARAM>(this);
+ psp.pszTitle = MAKEINTRESOURCE(IDS_PST_TAB_NAME);
+
+ hPage = CreatePropertySheetPage(&psp);
+ _ASSERT(hPage);
+
+ hr = lpProvider->AddPage(hPage);
+
+ return hr;
+}
+
+HRESULT Shib_PropSheet::QueryPagesFor(
+ /* [in] */ LPDATAOBJECT lpDataObject)
+{
+ return S_OK;
+}
+
+void Shib_PropSheet::Set_Delete_Button(int i) {
+
+ if (!_tcsicmp((directive[i].defined_in.c_str() + 1),pwzRegPath)) {
+ EnableWindow(hDelete,TRUE);
+ } else {
+ EnableWindow(hDelete,FALSE);
+ }
+}
+
+void Shib_PropSheet::ReadSelectedValue() {
+
+ DWORD index = SendMessage(hProps, CB_GETCURSEL, 0,0);
+ unsigned int i = SendMessage(hProps, CB_GETITEMDATA, (WPARAM)index, 0 );
+ directive[i].Set_Path(pwzRegPath);
+ directive[i].new_value = directive[i].value;
+
+}
+
+void Shib_PropSheet::ReadCurrentValues() {
+
+ for (int i=0;i<NUM_DIRECTIVES;i++) {
+ directive[i].Set_Path(pwzRegPath);
+ directive[i].new_value = directive[i].value;
+ }
+}
+
+
+void Shib_PropSheet::WriteValues() {
+ string RegPath;
+
+ RegPath = _T(SHIB_DEFAULT_WEB_KEY);
+
+ if (_tcslen(pwzRegPath)) {
+ RegPath += _T("\\");
+ RegPath += pwzRegPath;
+ ReplaceSlashes(RegPath);
+ }
+
+ for (int i=0;i<NUM_DIRECTIVES;i++) {
+ if (_tcscmp(STR_PENDING_DELETION,directive[i].new_value.c_str())){
+ if (_tcsicmp(directive[i].value.c_str(),directive[i].new_value.c_str())) {
+ directive[i].WriteValue(RegPath);
+ }
+ } else { // Commit Delete
+ directive[i].DeleteRegVal(RegPath);
+ }
+ }
+}
+
--- /dev/null
+
+#ifndef _Shib_PropSheet
+#define _Shib_PropSheet
+
+#include <tchar.h>
+#include <mmc.h>
+#include <string>
+using namespace std;
+
+#define D_FREE_STRING 0
+#define D_FREE_INT 1
+#define D_BOUND_INT 2
+#define D_BOUND_STRING 3
+
+typedef _TCHAR pool;
+
+#define STR_THIS_WEB_INSTANCE L"(This web instance)"
+#define STR_SERVER_DEFAULT L"(Server Default)"
+#define STR_PROGRAM_DEFAULT L"(Program Default)"
+
+#include "directives.h"
+#include "directive_class.h"
+
+#define debug_break() MessageBox(NULL,L"Break",L"Break",MB_OK);
+
+class Shib_PropSheet : public IExtendPropertySheet
+{
+
+public:
+ Shib_PropSheet();
+ ~Shib_PropSheet();
+
+ HWND hwndDlg;
+ LPTSTR pwzRegPath;
+ LPTSTR pwzMachineName;
+ Directive directive[NUM_DIRECTIVES];
+
+ void SetupPropSheet();
+ void PopulatePage();
+ BOOL UpdateNewValue();
+ void DeleteValue();
+ void GetHandles();
+
+ ///////////////////////////////
+ // Interface IUnknown
+ ///////////////////////////////
+ STDMETHODIMP QueryInterface(REFIID riid, LPVOID *ppv);
+ STDMETHODIMP_(ULONG) AddRef();
+ STDMETHODIMP_(ULONG) Release();
+
+ ///////////////////////////////
+ // Interface IExtendPropertySheet
+ ///////////////////////////////
+ virtual /* [helpstring] */ HRESULT STDMETHODCALLTYPE CreatePropertyPages(
+ /* [in] */ LPPROPERTYSHEETCALLBACK lpProvider,
+ /* [in] */ LONG_PTR handle,
+ /* [in] */ LPDATAOBJECT lpIDataObject);
+
+ virtual /* [helpstring] */ HRESULT STDMETHODCALLTYPE QueryPagesFor(
+ /* [in] */ LPDATAOBJECT lpDataObject);
+
+
+private:
+ LONG_PTR m_ppHandle;
+ LPTSTR pwzInstance;
+ LPTSTR pwzMetaPath;
+ LPTSTR pwzNode;
+ LPTSTR pwzParentPath;
+ LPTSTR pwzService;
+ pool p[MAX_REG_BUFF];
+ string defined_in;
+ HWND hValueBox;
+ HWND hValueEdit;
+ HWND hInheritedFrom;
+ HWND hMoreInfo;
+ HWND hProps;
+ HWND hDelete;
+ ULONG m_cref;
+
+ static BOOL CALLBACK DialogProc(HWND hwndDlg,
+ UINT uMsg,
+ WPARAM wParam,
+ LPARAM lParam
+ );
+
+ void PopulateComboBox();
+ void WriteValues();
+ void GetEffectiveValue(int i);
+ void ReplaceSlashes(string& buf);
+ void ReadCurrentValues();
+ void DeleteRegVal(const _TCHAR* szKey, const _TCHAR* szValueName);
+ void Set_Delete_Button(int i);
+ void ReadSelectedValue();
+ void ReadValAsString(LPTSTR key, int i, LPCTSTR defined_in);
+
+ ///////////////////////////////
+ // Private IDataObject support bits
+ ///////////////////////////////
+ HRESULT ExtractData( IDataObject* piDataObject,
+ CLIPFORMAT cfClipFormat,
+ BYTE* pbData,
+ DWORD cbData );
+
+ HRESULT ExtractWString( IDataObject *piDataObject,
+ CLIPFORMAT cfClipFormat,
+ WCHAR *pstr,
+ DWORD cchMaxLength)
+ {
+ return ExtractData( piDataObject, cfClipFormat, (PBYTE)pstr, cchMaxLength );
+ }
+
+};
+
+
+#endif _Shib_PropSheet_H_
--- /dev/null
+//==============================================================;
+//
+// This source code is only intended as a supplement to existing Microsoft documentation.
+//
+//
+//
+//
+// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF ANY
+// KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
+// IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A PARTICULAR
+// PURPOSE.
+//
+// Copyright (C) 1999 - 2001 Microsoft Corporation. All Rights Reserved.
+//
+//
+//
+//==============================================================;
+#include <Windows.h>
+/*
+ * AnsiToUnicode converts the ANSI string pszA to a Unicode string
+ * and returns the Unicode string through ppszW. Space for the
+ * the converted string is allocated by AnsiToUnicode.
+ */
+
+HRESULT __fastcall AnsiToUnicode(LPCSTR pszA, LPOLESTR* ppszW)
+{
+
+ ULONG cCharacters;
+ DWORD dwError;
+
+ // If input is null then just return the same.
+ if (NULL == pszA)
+ {
+ *ppszW = NULL;
+ return NOERROR;
+ }
+
+ // Determine number of wide characters to be allocated for the
+ // Unicode string.
+ cCharacters = strlen(pszA)+1;
+
+ // Use of the OLE allocator is required if the resultant Unicode
+ // string will be passed to another COM component and if that
+ // component will free it. Otherwise you can use your own allocator.
+ *ppszW = (LPOLESTR) CoTaskMemAlloc(cCharacters*2);
+ if (NULL == *ppszW)
+ return E_OUTOFMEMORY;
+
+ // Covert to Unicode.
+ if (0 == MultiByteToWideChar(CP_ACP, 0, pszA, cCharacters,
+ *ppszW, cCharacters))
+ {
+ dwError = GetLastError();
+ CoTaskMemFree(*ppszW);
+ *ppszW = NULL;
+ return HRESULT_FROM_WIN32(dwError);
+ }
+
+ return NOERROR;
+}
+
+/*
+ * UnicodeToAnsi converts the Unicode string pszW to an ANSI string
+ * and returns the ANSI string through ppszA. Space for the
+ * the converted string is allocated by UnicodeToAnsi.
+ */
+
+HRESULT __fastcall UnicodeToAnsi(LPCOLESTR pszW, LPSTR* ppszA)
+{
+
+ ULONG cbAnsi, cCharacters;
+ DWORD dwError;
+
+ // If input is null then just return the same.
+ if (pszW == NULL)
+ {
+ *ppszA = NULL;
+ return NOERROR;
+ }
+
+ cCharacters = wcslen(pszW)+1;
+ // Determine number of bytes to be allocated for ANSI string. An
+ // ANSI string can have at most 2 bytes per character (for Double
+ // Byte Character Strings.)
+ cbAnsi = cCharacters*2;
+
+ // Use of the OLE allocator is not required because the resultant
+ // ANSI string will never be passed to another COM component. You
+ // can use your own allocator.
+ *ppszA = (LPSTR) CoTaskMemAlloc(cbAnsi);
+ if (NULL == *ppszA)
+ return E_OUTOFMEMORY;
+
+ // Convert to ANSI.
+ if (0 == WideCharToMultiByte(CP_ACP, 0, pszW, cCharacters, *ppszA,
+ cbAnsi, NULL, NULL))
+ {
+ dwError = GetLastError();
+ CoTaskMemFree(*ppszA);
+ *ppszA = NULL;
+ return HRESULT_FROM_WIN32(dwError);
+ }
+ return NOERROR;
+
+}
\ No newline at end of file
--- /dev/null
+//==============================================================;
+//
+// This source code is only intended as a supplement to existing Microsoft documentation.
+//
+//
+//
+//
+// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF ANY
+// KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
+// IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A PARTICULAR
+// PURPOSE.
+//
+// Copyright (C) 1999 - 2001 Microsoft Corporation. All Rights Reserved.
+//
+//
+//
+//==============================================================;
+/*
+ * AnsiToUnicode converts the ANSI string pszA to a Unicode string
+ * and returns the Unicode string through ppszW. Space for the
+ * the converted string is allocated by AnsiToUnicode.
+ */
+
+HRESULT __fastcall AnsiToUnicode(LPCSTR pszA, LPOLESTR* ppszW);
+
+/*
+ * UnicodeToAnsi converts the Unicode string pszW to an ANSI string
+ * and returns the ANSI string through ppszA. Space for the
+ * the converted string is allocated by UnicodeToAnsi.
+ */
+
+HRESULT __fastcall UnicodeToAnsi(LPCOLESTR pszW, LPSTR* ppszA);
--- /dev/null
+//==============================================================;
+//
+// This source code is only intended as a supplement to existing Microsoft documentation.
+//
+//
+//
+//
+// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF ANY
+// KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
+// IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A PARTICULAR
+// PURPOSE.
+//
+// Copyright (C) 1999 - 2001 Microsoft Corporation. All Rights Reserved.
+//
+//
+//
+//==============================================================;
+
+#include <objbase.h>
+#include <olectl.h>
+#include <initguid.h>
+#include "globals.h"
+#include "resource.h"
+#include "guids.h"
+#include "basesnap.h"
+#include "Shib_PropSheet.h"
+#include "Registry.h"
+#include "Extend.h"
+
+// our globals
+HINSTANCE g_hinst;
+
+
+BOOL WINAPI DllMain(HINSTANCE hinstDLL,
+ DWORD fdwReason,
+ void* lpvReserved)
+{
+
+ if (fdwReason == DLL_PROCESS_ATTACH) {
+ g_hinst = hinstDLL;
+ }
+
+ return TRUE;
+}
+
+
+STDAPI DllGetClassObject(REFCLSID rclsid, REFIID riid, LPVOID *ppvObj)
+{
+ if (rclsid != CLSID_Shib_PropSheet)
+ return CLASS_E_CLASSNOTAVAILABLE;
+
+
+ if (!ppvObj)
+ return E_FAIL;
+
+ *ppvObj = NULL;
+
+ // We can only hand out IUnknown and IClassFactory pointers. Fail
+ // if they ask for anything else.
+ if (!IsEqualIID(riid, IID_IUnknown) && !IsEqualIID(riid, IID_IClassFactory))
+ return E_NOINTERFACE;
+
+ CClassFactory *pFactory = NULL;
+
+ // make the factory passing in the creation function for the type of object they want
+ if (rclsid == CLSID_Shib_PropSheet)
+ pFactory = new CClassFactory(CClassFactory::CONTEXTEXTENSION);
+
+ if (NULL == pFactory)
+ return E_OUTOFMEMORY;
+
+ HRESULT hr = pFactory->QueryInterface(riid, ppvObj);
+
+ return hr;
+}
+
+STDAPI DllCanUnloadNow(void)
+{
+ if (g_uObjects == 0 && g_uSrvLock == 0)
+ return S_OK;
+ else
+ return S_FALSE;
+}
+
+
+CClassFactory::CClassFactory(FACTORY_TYPE factoryType)
+: m_cref(0), m_factoryType(factoryType)
+{
+ OBJECT_CREATED
+}
+
+CClassFactory::~CClassFactory()
+{
+ OBJECT_DESTROYED
+}
+
+STDMETHODIMP CClassFactory::QueryInterface(REFIID riid, LPVOID *ppv)
+{
+ if (!ppv)
+ return E_FAIL;
+
+ *ppv = NULL;
+
+ if (IsEqualIID(riid, IID_IUnknown))
+ *ppv = static_cast<IClassFactory *>(this);
+ else
+ if (IsEqualIID(riid, IID_IClassFactory))
+ *ppv = static_cast<IClassFactory *>(this);
+
+ if (*ppv)
+ {
+ reinterpret_cast<IUnknown *>(*ppv)->AddRef();
+ return S_OK;
+ }
+
+ return E_NOINTERFACE;
+}
+
+STDMETHODIMP_(ULONG) CClassFactory::AddRef()
+{
+ return InterlockedIncrement((LONG *)&m_cref);
+}
+
+STDMETHODIMP_(ULONG) CClassFactory::Release()
+{
+ if (InterlockedDecrement((LONG *)&m_cref) == 0)
+ {
+ delete this;
+ return 0;
+ }
+ return m_cref;
+}
+
+STDMETHODIMP CClassFactory::CreateInstance(LPUNKNOWN pUnkOuter, REFIID riid, LPVOID * ppvObj)
+{
+ HRESULT hr;
+ void* pObj;
+
+ if (!ppvObj)
+ return E_FAIL;
+
+ *ppvObj = NULL;
+
+ // Our object does does not support aggregation, so we need to
+ // fail if they ask us to do aggregation.
+ if (pUnkOuter)
+ return CLASS_E_NOAGGREGATION;
+ pObj = new Shib_PropSheet();
+
+ if (!pObj)
+ return E_OUTOFMEMORY;
+
+ // QueryInterface will do the AddRef() for us, so we do not
+ // do it in this function
+ hr = ((LPUNKNOWN)pObj)->QueryInterface(riid, ppvObj);
+
+ if (FAILED(hr))
+ delete pObj;
+
+ return hr;
+}
+
+STDMETHODIMP CClassFactory::LockServer(BOOL fLock)
+{
+ if (fLock)
+ InterlockedIncrement((LONG *)&g_uSrvLock);
+ else
+ InterlockedDecrement((LONG *)&g_uSrvLock);
+
+ return S_OK;
+}
+
+//////////////////////////////////////////////////////////
+//
+// Exported functions
+//
+
+
+//
+// Server registration
+//
+STDAPI DllRegisterServer()
+{
+ HRESULT hr = SELFREG_E_CLASS;
+
+ _TCHAR szName[256];
+ _TCHAR szSnapInName[256];
+
+ LoadString(g_hinst, IDS_NAME, szName, (sizeof szName)/(sizeof szName[0]));
+ LoadString(g_hinst, IDS_SNAPINNAME, szSnapInName, (sizeof szSnapInName)/(sizeof szSnapInName[0]));
+
+ /* _TCHAR szAboutName[256];
+
+ LoadString(g_hinst, IDS_ABOUTNAME, szAboutName, (sizeof szAboutName)/(sizeof szAboutName[0]));
+ */
+
+ // register our CoClasses
+ hr = RegisterServer(g_hinst,
+ CLSID_Shib_PropSheet,
+ szName);
+
+ // place the registry information for SnapIns
+ if SUCCEEDED(hr)
+ hr = RegisterSnapin(CLSID_Shib_PropSheet, szSnapInName);
+
+ return hr;
+}
+
+
+STDAPI DllUnregisterServer()
+{
+ if (UnregisterServer(CLSID_Shib_PropSheet) == S_OK)
+ return UnregisterSnapin(CLSID_Shib_PropSheet);
+ else
+ return E_FAIL;
+}
+
--- /dev/null
+
+EXPORTS
+ DllGetClassObject PRIVATE
+ DllCanUnloadNow PRIVATE
+ DllRegisterServer PRIVATE
+ DllUnregisterServer PRIVATE
--- /dev/null
+//==============================================================;
+//
+// This source code is only intended as a supplement to existing Microsoft documentation.
+//
+//
+//
+//
+// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF ANY
+// KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
+// IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A PARTICULAR
+// PURPOSE.
+//
+// Copyright (C) 1999 - 2001 Microsoft Corporation. All Rights Reserved.
+//
+//
+//
+//==============================================================;
+#ifndef _BASESNAP_H_
+#define _BASESNAP_H_
+
+STDAPI DllGetClassObject(REFCLSID rclsid, REFIID riid, LPVOID *ppvObj);
+STDAPI DllCanUnloadNow(void);
+
+ULONG g_uObjects = 0;
+ULONG g_uSrvLock = 0;
+
+class CClassFactory : public IClassFactory
+{
+private:
+ ULONG m_cref;
+
+public:
+ enum FACTORY_TYPE {CONTEXTEXTENSION = 0, ABOUT = 1};
+
+ CClassFactory(FACTORY_TYPE factoryType);
+ ~CClassFactory();
+
+ STDMETHODIMP QueryInterface(REFIID riid, LPVOID *ppv);
+ STDMETHODIMP_(ULONG) AddRef();
+ STDMETHODIMP_(ULONG) Release();
+
+ STDMETHODIMP CreateInstance(LPUNKNOWN, REFIID, LPVOID *);
+ STDMETHODIMP LockServer(BOOL);
+
+private:
+ FACTORY_TYPE m_factoryType;
+};
+
+#endif _BASESNAP_H_
--- /dev/null
+//==============================================================;
+//
+// This source code is only intended as a supplement to
+// existing Microsoft documentation.
+//
+//
+//
+//
+// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF ANY
+// KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
+// IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A PARTICULAR
+// PURPOSE.
+//
+// Copyright (C) 1999 - 2001 Microsoft Corporation. All Rights Reserved.
+//
+//
+//
+//==============================================================;
+
+#ifndef _EXTEND_H
+#define _EXTEND_H
+
+struct EXTENSION_NODE
+{
+ GUID GUID;
+ _TCHAR szDescription[256];
+};
+
+enum EXTENSION_TYPE
+{
+ NameSpaceExtension,
+ ContextMenuExtension,
+ ToolBarExtension,
+ PropertySheetExtension,
+ TaskExtension,
+ DynamicExtension,
+ DummyExtension
+};
+
+struct EXTENDER_NODE
+{
+ EXTENSION_TYPE eType;
+ GUID guidNode;
+ GUID guidExtension;
+ _TCHAR szDescription[256];
+};
+
+#endif // _EXTEND_H
+
+
--- /dev/null
+//==============================================================;
+//
+// This source code is only intended as a supplement to existing Microsoft documentation.
+//
+//
+//
+//
+// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF ANY
+// KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
+// IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A PARTICULAR
+// PURPOSE.
+//
+// Copyright (C) 1999 - 2001 Microsoft Corporation. All Rights Reserved.
+//
+//
+//
+//==============================================================;
+
+#ifndef _MMC_GLOBALS_H
+#define _MMC_GLOBALS_H
+
+#include <tchar.h>
+
+#ifndef STRINGS_ONLY
+ #define IDM_BUTTON1 0x100
+ #define IDM_BUTTON2 0x101
+
+ extern HINSTANCE g_hinst;
+ extern ULONG g_uObjects;
+
+ #define OBJECT_CREATED InterlockedIncrement((long *)&g_uObjects);
+ #define OBJECT_DESTROYED InterlockedDecrement((long *)&g_uObjects);
+
+#endif
+
+//=--------------------------------------------------------------------------=
+// allocates a temporary buffer that will disappear when it goes out of scope
+// NOTE: be careful of that -- make sure you use the string in the same or
+// nested scope in which you created this buffer. people should not use this
+// class directly. use the macro(s) below.
+//
+class TempBuffer {
+ public:
+ TempBuffer(ULONG cBytes) {
+ m_pBuf = (cBytes <= 120) ? &m_szTmpBuf : HeapAlloc(GetProcessHeap(), 0, cBytes);
+ m_fHeapAlloc = (cBytes > 120);
+ }
+ ~TempBuffer() {
+ if (m_pBuf && m_fHeapAlloc) HeapFree(GetProcessHeap(), 0, m_pBuf);
+ }
+ void *GetBuffer() {
+ return m_pBuf;
+ }
+
+ private:
+ void *m_pBuf;
+ // we'll use this temp buffer for small cases.
+ //
+ char m_szTmpBuf[120];
+ unsigned m_fHeapAlloc:1;
+};
+
+//=--------------------------------------------------------------------------=
+// string helpers.
+//
+// given a _TCHAR, copy it into a wide buffer.
+// be careful about scoping when using this macro!
+//
+// how to use the below two macros:
+//
+// ...
+// LPTSTR pszT;
+// pszT = MyGetTStringRoutine();
+// MAKE_WIDEPTR_FROMSTR(pwsz, pszT);
+// MyUseWideStringRoutine(pwsz);
+// ...
+#ifdef UNICODE
+#define MAKE_WIDEPTR_FROMTSTR(ptrname, tstr) \
+ long __l##ptrname = (lstrlenW(tstr) + 1) * sizeof(WCHAR); \
+ TempBuffer __TempBuffer##ptrname(__l##ptrname); \
+ lstrcpyW((LPWSTR)__TempBuffer##ptrname.GetBuffer(), tstr); \
+ LPWSTR ptrname = (LPWSTR)__TempBuffer##ptrname.GetBuffer()
+#else // ANSI
+#define MAKE_WIDEPTR_FROMTSTR(ptrname, tstr) \
+ long __cch##ptrname = (lstrlenA(tstr) + 1);\
+ long __l##ptrname = (lstrlenA(tstr) + 1) * sizeof(WCHAR); \
+ TempBuffer __TempBuffer##ptrname(__l##ptrname); \
+ MultiByteToWideChar(CP_ACP, 0, tstr, -1, (LPWSTR)__TempBuffer##ptrname.GetBuffer(), __cch##ptrname); \
+ LPWSTR ptrname = (LPWSTR)__TempBuffer##ptrname.GetBuffer()
+#endif
+
+#ifdef UNICODE
+#define MAKE_WIDEPTR_FROMTSTR_ALLOC(ptrname, tstr) \
+ long __l##ptrname = (lstrlenW(tstr) + 1) * sizeof(WCHAR); \
+ LPWSTR ptrname = (LPWSTR)CoTaskMemAlloc(__l##ptrname); \
+ lstrcpyW((LPWSTR)ptrname, tstr)
+#else // ANSI
+#define MAKE_WIDEPTR_FROMTSTR_ALLOC(ptrname, tstr) \
+ long __cch##ptrname = (lstrlenA(tstr) + 1);\
+ long __l##ptrname = (lstrlenA(tstr) + 1) * sizeof(WCHAR); \
+ LPWSTR ptrname = (LPWSTR)CoTaskMemAlloc(__l##ptrname); \
+ MultiByteToWideChar(CP_ACP, 0, tstr, -1, ptrname, __cch##ptrname)
+#endif
+
+//
+// similarily for MAKE_TSTRPTR_FROMWIDE. note that the first param does not
+// have to be declared, and no clean up must be done.
+//
+// * 2 for DBCS handling in below length computation
+//
+#ifdef UNICODE
+#define MAKE_TSTRPTR_FROMWIDE(ptrname, widestr) \
+ long __l##ptrname = (wcslen(widestr) + 1) * 2 * sizeof(TCHAR); \
+ TempBuffer __TempBuffer##ptrname(__l##ptrname); \
+ lstrcpyW((LPTSTR)__TempBuffer##ptrname.GetBuffer(), widestr); \
+ LPTSTR ptrname = (LPTSTR)__TempBuffer##ptrname.GetBuffer()
+#else // ANSI
+#define MAKE_TSTRPTR_FROMWIDE(ptrname, widestr) \
+ long __l##ptrname = (wcslen(widestr) + 1) * 2 * sizeof(TCHAR); \
+ TempBuffer __TempBuffer##ptrname(__l##ptrname); \
+ WideCharToMultiByte(CP_ACP, 0, widestr, -1, (LPSTR)__TempBuffer##ptrname.GetBuffer(), __l##ptrname, NULL, NULL); \
+ LPTSTR ptrname = (LPTSTR)__TempBuffer##ptrname.GetBuffer()
+#endif
+
+#endif // _MMC_GLOBALS_H
--- /dev/null
+//Microsoft Developer Studio generated resource script.
+//
+#include "resource.h"
+
+#define APSTUDIO_READONLY_SYMBOLS
+/////////////////////////////////////////////////////////////////////////////
+//
+// Generated from the TEXTINCLUDE 2 resource.
+//
+#include "winres.h"
+
+/////////////////////////////////////////////////////////////////////////////
+#undef APSTUDIO_READONLY_SYMBOLS
+
+/////////////////////////////////////////////////////////////////////////////
+// English (U.S.) resources
+
+#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU)
+#ifdef _WIN32
+LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US
+#pragma code_page(1252)
+#endif //_WIN32
+
+#ifdef APSTUDIO_INVOKED
+/////////////////////////////////////////////////////////////////////////////
+//
+// TEXTINCLUDE
+//
+
+1 TEXTINCLUDE MOVEABLE PURE
+BEGIN
+ "resource.h\0"
+END
+
+2 TEXTINCLUDE MOVEABLE PURE
+BEGIN
+ "#include ""winres.h""\r\n"
+ "\0"
+END
+
+3 TEXTINCLUDE MOVEABLE PURE
+BEGIN
+ "\r\n"
+ "\0"
+END
+
+#endif // APSTUDIO_INVOKED
+
+
+/////////////////////////////////////////////////////////////////////////////
+//
+// Dialog
+//
+
+IDD_PROPPAGE DIALOG DISCARDABLE 0, 0, 284, 215
+STYLE WS_CHILD | WS_DISABLED | WS_CAPTION
+CAPTION "Property Page"
+FONT 8, "MS Sans Serif"
+BEGIN
+ GROUPBOX "More Information",IDC_STATIC,3,130,275,81
+ COMBOBOX IDC_PROPS,5,23,121,105,CBS_DROPDOWNLIST | CBS_SORT |
+ WS_VSCROLL | WS_TABSTOP
+ LTEXT "Directive",IDC_NAME,5,6,116,11
+ LTEXT "Value",IDC_STATIC,144,7,116,11
+ COMBOBOX IDC_ValueBox,143,23,134,89,CBS_DROPDOWN | CBS_SORT |
+ WS_VSCROLL | WS_TABSTOP
+ LTEXT "Static",IDC_MoreInfo,11,143,260,61
+ EDITTEXT IDC_ValueEdit,143,23,134,14,ES_AUTOHSCROLL
+ LTEXT "Static",IDC_InheritedFrom,146,73,130,31
+ LTEXT "Inherited from:",IDC_InheritedFromStatic,143,58,116,11
+ PUSHBUTTON "Remove value from this location",IDC_Delete,143,105,123,
+ 18,WS_DISABLED
+ PUSHBUTTON "Refresh/reload current values",IDC_Refresh,12,105,113,
+ 18,NOT WS_VISIBLE
+END
+
+
+#ifndef _MAC
+/////////////////////////////////////////////////////////////////////////////
+//
+// Version
+//
+
+VS_VERSION_INFO VERSIONINFO
+ FILEVERSION 1,0,0,1
+ PRODUCTVERSION 1,0,0,1
+ FILEFLAGSMASK 0x17L
+#ifdef _DEBUG
+ FILEFLAGS 0x1L
+#else
+ FILEFLAGS 0x0L
+#endif
+ FILEOS 0x4L
+ FILETYPE 0x2L
+ FILESUBTYPE 0x0L
+BEGIN
+ BLOCK "StringFileInfo"
+ BEGIN
+ BLOCK "040904b0"
+ BEGIN
+ VALUE "Comments", "\0"
+ VALUE "CompanyName", "Internet 2\0"
+ VALUE "FileDescription", "Shibboleth GUI Snap-In for IIS console\0"
+ VALUE "FileVersion", "1, 0, 0, 1\0"
+ VALUE "InternalName", "\0"
+ VALUE "LegalCopyright", "Copyright (C) 2004\0"
+ VALUE "LegalTrademarks", "\0"
+ VALUE "OriginalFilename", "\0"
+ VALUE "PrivateBuild", "\0"
+ VALUE "ProductName", "Shibboleth\0"
+ VALUE "ProductVersion", "1, 0, 0, 1\0"
+ VALUE "SpecialBuild", "\0"
+ END
+ END
+ BLOCK "VarFileInfo"
+ BEGIN
+ VALUE "Translation", 0x409, 1200
+ END
+END
+
+#endif // !_MAC
+
+
+/////////////////////////////////////////////////////////////////////////////
+//
+// String Table
+//
+
+STRINGTABLE DISCARDABLE
+BEGIN
+ IDS_NAME "Shibboleth Directive Snap-in"
+ IDS_SNAPINNAME "Shibboleth Directive Snap-in"
+ IDS_PST_TAB_NAME "Shibboleth Directives"
+END
+
+#endif // English (U.S.) resources
+/////////////////////////////////////////////////////////////////////////////
+
+
+
+#ifndef APSTUDIO_INVOKED
+/////////////////////////////////////////////////////////////////////////////
+//
+// Generated from the TEXTINCLUDE 3 resource.
+//
+
+
+/////////////////////////////////////////////////////////////////////////////
+#endif // not APSTUDIO_INVOKED
+
--- /dev/null
+# Microsoft Developer Studio Project File - Name="isapi_shib_gui" - Package Owner=<4>
+# Microsoft Developer Studio Generated Build File, Format Version 6.00
+# ** DO NOT EDIT **
+
+# TARGTYPE "Win32 (x86) Dynamic-Link Library" 0x0102
+
+CFG=isapi_shib_gui - Win32 Debug
+!MESSAGE This is not a valid makefile. To build this project using NMAKE,
+!MESSAGE use the Export Makefile command and run
+!MESSAGE
+!MESSAGE NMAKE /f "isapi_shib_gui.mak".
+!MESSAGE
+!MESSAGE You can specify a configuration when running NMAKE
+!MESSAGE by defining the macro CFG on the command line. For example:
+!MESSAGE
+!MESSAGE NMAKE /f "isapi_shib_gui.mak" CFG="isapi_shib_gui - Win32 Debug"
+!MESSAGE
+!MESSAGE Possible choices for configuration are:
+!MESSAGE
+!MESSAGE "isapi_shib_gui - Win32 Release" (based on "Win32 (x86) Dynamic-Link Library")
+!MESSAGE "isapi_shib_gui - Win32 Debug" (based on "Win32 (x86) Dynamic-Link Library")
+!MESSAGE
+
+# Begin Project
+# PROP AllowPerConfigDependencies 0
+# PROP Scc_ProjName ""
+# PROP Scc_LocalPath ""
+CPP=cl.exe
+MTL=midl.exe
+RSC=rc.exe
+
+!IF "$(CFG)" == "isapi_shib_gui - Win32 Release"
+
+# PROP BASE Use_MFC 0
+# PROP BASE Use_Debug_Libraries 0
+# PROP BASE Output_Dir "isapi_shib_gui___Win32_Release"
+# PROP BASE Intermediate_Dir "isapi_shib_gui___Win32_Release"
+# PROP BASE Ignore_Export_Lib 0
+# PROP BASE Target_Dir ""
+# PROP Use_MFC 0
+# PROP Use_Debug_Libraries 0
+# PROP Output_Dir "Release"
+# PROP Intermediate_Dir "Release"
+# PROP Ignore_Export_Lib 0
+# PROP Target_Dir ""
+# ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "isapi_shib_gui_EXPORTS" /FD /c
+# SUBTRACT BASE CPP /YX
+# ADD CPP /nologo /MT /W3 /GX /O2 /I "..\isapi_shib" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "isapi_shib_gui_EXPORTS" /FR /FD /c
+# SUBTRACT CPP /YX
+# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32
+# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32
+# ADD BASE RSC /l 0x409 /d "NDEBUG"
+# ADD RSC /l 0x409 /d "NDEBUG"
+BSC32=bscmake.exe
+# ADD BASE BSC32 /nologo /o"Release/shib_gui.bsc"
+# ADD BSC32 /nologo /o"Release/shib_gui.bsc"
+LINK32=link.exe
+# ADD BASE LINK32 comctl32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib mmc.lib /nologo /base:"0x13000000" /dll /machine:I386 /out:"Release/shib_gui.dll"
+# ADD LINK32 comctl32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib mmc.lib /nologo /base:"0x13000000" /dll /machine:I386 /out:"Release/shib_gui.dll"
+# Begin Custom Build - Performing Registrations
+OutDir=.\Release
+TargetPath=.\Release\shib_gui.dll
+InputPath=.\Release\shib_gui.dll
+SOURCE="$(InputPath)"
+
+"$(OutDir)\regsvr32.trg" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ regsvr32 /s /c "$(TargetPath)"
+ echo regsvr32 exec. time > "$(OutDir)\regsvr32.trg"
+
+# End Custom Build
+
+!ELSEIF "$(CFG)" == "isapi_shib_gui - Win32 Debug"
+
+# PROP BASE Use_MFC 0
+# PROP BASE Use_Debug_Libraries 1
+# PROP BASE Output_Dir "isapi_shib_gui___Win32_Debug"
+# PROP BASE Intermediate_Dir "isapi_shib_gui___Win32_Debug"
+# PROP BASE Ignore_Export_Lib 0
+# PROP BASE Target_Dir ""
+# PROP Use_MFC 0
+# PROP Use_Debug_Libraries 1
+# PROP Output_Dir "Debug"
+# PROP Intermediate_Dir "Debug"
+# PROP Ignore_Export_Lib 0
+# PROP Target_Dir ""
+# ADD BASE CPP /nologo /MTd /W3 /Gm /GR /GX /ZI /Od /I "..\isapi_shib" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_USRDLL" /FR /FD /c
+# SUBTRACT BASE CPP /YX
+# ADD CPP /nologo /MTd /W3 /Gm /GR /GX /ZI /Od /I "..\isapi_shib" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_USRDLL" /FR /FD /c
+# SUBTRACT CPP /YX
+# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32
+# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32
+# ADD BASE RSC /l 0x409 /d "_DEBUG"
+# ADD RSC /l 0x409 /d "_DEBUG"
+BSC32=bscmake.exe
+# ADD BASE BSC32 /nologo /o"debug/shib_gui.bsc"
+# ADD BSC32 /nologo /o"debug/shib_gui.bsc"
+LINK32=link.exe
+# ADD BASE LINK32 COMCTL32.LIB kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib mmc.lib /nologo /base:"0x13000000" /dll /debug /machine:I386 /out:"debug/shib_gui.dll"
+# ADD LINK32 COMCTL32.LIB kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib mmc.lib /nologo /base:"0x13000000" /dll /debug /machine:I386 /out:"debug/shib_gui.dll"
+# Begin Custom Build - Performing Registrations
+OutDir=.\Debug
+TargetPath=.\debug\shib_gui.dll
+InputPath=.\debug\shib_gui.dll
+SOURCE="$(InputPath)"
+
+"$(OutDir)\regsvr32.trg" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ regsvr32 /s /c "$(TargetPath)"
+ echo regsvr32 exec. time > "$(OutDir)\regsvr32.trg"
+
+# End Custom Build
+
+!ENDIF
+
+# Begin Target
+
+# Name "isapi_shib_gui - Win32 Release"
+# Name "isapi_shib_gui - Win32 Debug"
+# Begin Group "Source Files"
+
+# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat"
+# Begin Source File
+
+SOURCE=.\atou.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\basesnap.Cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\registry.Cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\Shib_PropSheet.cpp
+# End Source File
+# End Group
+# Begin Group "Header Files"
+
+# PROP Default_Filter "h;hpp;hxx;hm;inl"
+# Begin Source File
+
+SOURCE=.\atou.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\basesnap.Def
+# End Source File
+# Begin Source File
+
+SOURCE=.\basesnap.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\isapi_shib\directive_class.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\isapi_shib\directives.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\GUIDs.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\Shib_PropSheet.h
+# End Source File
+# End Group
+# Begin Group "Resource Files"
+
+# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe"
+# Begin Source File
+
+SOURCE=.\isapi_gui.Rc
+# End Source File
+# End Group
+# End Target
+# End Project
--- /dev/null
+//==============================================================;
+//
+// This source code is only intended as a supplement to existing Microsoft documentation.
+//
+//
+//
+//
+// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF ANY
+// KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
+// IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A PARTICULAR
+// PURPOSE.
+//
+// Copyright (C) 1999 - 2001 Microsoft Corporation. All Rights Reserved.
+//
+//
+//
+//==============================================================;
+
+#include <objbase.h>
+#include <assert.h>
+#include "Registry.h"
+#include "Extend.h"
+#include "GUIDs.h"
+#include "globals.h"
+
+// if not standalone comment out next line
+//#define STANDALONE
+
+// list all nodes that are extendable here
+// List the GUID and then the description
+// terminate with a NULL, NULL set.
+EXTENSION_NODE _ExtendableNodes[] = {
+ {NULL, NULL}
+};
+// list all of the nodes that we extend
+EXTENDER_NODE _NodeExtensions[] =
+ PBC_EXTENDER_NODES;
+
+////////////////////////////////////////////////////////
+//
+// Internal helper functions prototypes
+//
+
+// Set the given key and its value.
+BOOL setKeyAndValue(const _TCHAR* pszPath,
+ const _TCHAR* szSubkey,
+ const _TCHAR* szValue) ;
+
+// Set the given key and its value in the MMC Snapin location
+BOOL setSnapInKeyAndValue(const _TCHAR* szKey,
+ const _TCHAR* szSubkey,
+ const _TCHAR* szName,
+ const _TCHAR* szValue);
+
+// Set the given valuename under the key to value
+BOOL setValue(const _TCHAR* szKey,
+ const _TCHAR* szValueName,
+ const _TCHAR* szValue);
+
+BOOL setSnapInExtensionNode(const _TCHAR* szSnapID,
+ const _TCHAR* szNodeID,
+ const _TCHAR* szDescription);
+
+// Delete szKeyChild and all of its descendents.
+LONG recursiveDeleteKey(HKEY hKeyParent, const _TCHAR* szKeyChild) ;
+
+////////////////////////////////////////////////////////
+//
+// Constants
+//
+
+// Size of a CLSID as a string
+//const int CLSID_STRING_SIZE = 39 ;
+
+/////////////////////////////////////////////////////////
+//
+// Public function implementation
+//
+
+//
+// Register the component in the registry.
+//
+HRESULT RegisterServer(HMODULE hModule, // DLL module handle
+ const CLSID& clsid, // Class ID
+ const _TCHAR* szFriendlyName) // IDs
+{
+ // Get server location.
+ _TCHAR szModule[512] ;
+ DWORD dwResult =
+ ::GetModuleFileName(hModule,
+ szModule,
+ sizeof(szModule)/sizeof(_TCHAR)) ;
+
+ assert(dwResult != 0) ;
+
+ // Get CLSID
+ LPOLESTR wszCLSID = NULL ;
+ HRESULT hr = StringFromCLSID(clsid, &wszCLSID) ;
+
+ assert(SUCCEEDED(hr)) ;
+
+ MAKE_TSTRPTR_FROMWIDE(pszCLSID, wszCLSID);
+
+ // Build the key CLSID\\{...}
+ _TCHAR szKey[64] ;
+ _tcscpy(szKey, _T("CLSID\\")) ;
+ _tcscat(szKey, pszCLSID) ;
+
+ // Add the CLSID to the registry.
+ setKeyAndValue(szKey, NULL, szFriendlyName) ;
+
+ // Add the server filename subkey under the CLSID key.
+ setKeyAndValue(szKey, _T("InprocServer32"), szModule) ;
+
+ // set the threading model
+ _tcscat(szKey, _T("\\InprocServer32"));
+ setValue(szKey, _T("ThreadingModel"), _T("Apartment"));
+
+ // Free memory.
+ CoTaskMemFree(wszCLSID) ;
+
+ return S_OK ;
+}
+
+//
+// Remove the component from the registry.
+//
+LONG UnregisterServer(const CLSID& clsid) // IDs
+{
+ // Get CLSID
+ LPOLESTR wszCLSID = NULL ;
+ HRESULT hr = StringFromCLSID(clsid, &wszCLSID) ;
+
+
+ // Build the key CLSID\\{...}
+ _TCHAR szKey[64] ;
+ _tcscpy(szKey, _T("CLSID\\")) ;
+
+ MAKE_TSTRPTR_FROMWIDE(pszT, wszCLSID);
+ _tcscat(szKey, pszT) ;
+
+ // Delete the CLSID Key - CLSID\{...}
+ LONG lResult = recursiveDeleteKey(HKEY_CLASSES_ROOT, szKey) ;
+ assert((lResult == ERROR_SUCCESS) ||
+ (lResult == ERROR_FILE_NOT_FOUND)) ; // Subkey may not exist.
+
+ // Free memory.
+ CoTaskMemFree(wszCLSID) ;
+
+ return S_OK ;
+}
+
+//
+// Register the snap-in in the registry.
+//
+HRESULT RegisterSnapin(const CLSID& clsid, // Class ID
+ const _TCHAR* szNameString)
+{
+ // Get CLSID
+ LPOLESTR wszCLSID = NULL ;
+ LPOLESTR wszAboutCLSID = NULL;
+ LPOLESTR wszExtendCLSID = NULL;
+ LPOLESTR wszNodeCLSID = NULL;
+ EXTENSION_NODE *pExtensionNode;
+ EXTENDER_NODE *pNodeExtension;
+ _TCHAR szKeyBuf[1024] ;
+ HKEY hKey;
+
+ HRESULT hr = StringFromCLSID(clsid, &wszCLSID) ;
+
+ MAKE_TSTRPTR_FROMWIDE(pszCLSID, wszCLSID);
+
+ // Add the CLSID to the registry.
+ setSnapInKeyAndValue(pszCLSID, NULL, _T("NameString"), szNameString) ;
+
+#ifdef STANDALONE
+ setSnapInKeyAndValue(pszCLSID, _T("StandAlone"), NULL, NULL);
+#endif
+
+ // register each of the node types in _ExtendableNodes as an extendable node
+ for (pExtensionNode = &(_ExtendableNodes[0]);*pExtensionNode->szDescription;pExtensionNode++)
+ {
+ hr = StringFromCLSID(pExtensionNode->GUID, &wszExtendCLSID);
+ MAKE_TSTRPTR_FROMWIDE(pszExtendCLSID, wszExtendCLSID);
+ setSnapInExtensionNode(pszCLSID, pszExtendCLSID, pExtensionNode->szDescription);
+ CoTaskMemFree(wszExtendCLSID);
+ }
+
+ // register each of the node extensions
+ for (pNodeExtension = &(_NodeExtensions[0]);*pNodeExtension->szDescription;pNodeExtension++)
+ {
+ hr = StringFromCLSID(pNodeExtension->guidNode, &wszExtendCLSID);
+ MAKE_TSTRPTR_FROMWIDE(pszExtendCLSID, wszExtendCLSID);
+ _tcscpy(szKeyBuf, _T("SOFTWARE\\Microsoft\\MMC\\NodeTypes\\"));
+ _tcscat(szKeyBuf, pszExtendCLSID);
+
+ switch (pNodeExtension->eType) {
+ case NameSpaceExtension:
+ _tcscat(szKeyBuf, _T("\\Extensions\\NameSpace"));
+ break;
+ case ContextMenuExtension:
+ _tcscat(szKeyBuf, _T("\\Extensions\\ContextMenu"));
+ break;
+ case ToolBarExtension:
+ _tcscat(szKeyBuf, _T("\\Extensions\\ToolBar"));
+ break;
+ case PropertySheetExtension:
+ _tcscat(szKeyBuf, _T("\\Extensions\\PropertySheet"));
+ break;
+ case TaskExtension:
+ _tcscat(szKeyBuf, _T("\\Extensions\\Task"));
+ break;
+ case DynamicExtension:
+ _tcscat(szKeyBuf, _T("\\Dynamic Extensions"));
+ default:
+ break;
+ }
+
+ // Create and open key and subkey.
+ long lResult = RegCreateKeyEx(HKEY_LOCAL_MACHINE ,
+ szKeyBuf,
+ 0, NULL, REG_OPTION_NON_VOLATILE,
+ KEY_ALL_ACCESS, NULL,
+ &hKey, NULL) ;
+
+ if (lResult != ERROR_SUCCESS)
+ {
+ return FALSE ;
+ }
+
+ hr = StringFromCLSID(pNodeExtension->guidExtension, &wszNodeCLSID);
+ assert(SUCCEEDED(hr));
+
+ MAKE_TSTRPTR_FROMWIDE(pszNodeCLSID, wszNodeCLSID);
+ // Set the Value.
+ if (pNodeExtension->szDescription != NULL)
+ {
+ RegSetValueEx(hKey, pszNodeCLSID, 0, REG_SZ,
+ (BYTE *)pNodeExtension->szDescription,
+ (_tcslen(pNodeExtension->szDescription)+1)*sizeof(_TCHAR)) ;
+ }
+
+ RegCloseKey(hKey) ;
+
+ CoTaskMemFree(wszExtendCLSID);
+ CoTaskMemFree(wszNodeCLSID);
+ }
+
+
+ // Free memory.
+ CoTaskMemFree(wszCLSID) ;
+ return S_OK ;
+}
+
+//
+// Unregister the snap-in in the registry.
+//
+HRESULT UnregisterSnapin(const CLSID& clsid) // Class ID
+{
+ _TCHAR szKeyBuf[1024];
+ LPOLESTR wszCLSID = NULL;
+
+ // Get CLSID
+ HRESULT hr = StringFromCLSID(clsid, &wszCLSID);
+ MAKE_TSTRPTR_FROMWIDE(pszCLSID, wszCLSID);
+ // Load the buffer with the Snap-In Location
+ _tcscpy(szKeyBuf, _T("SOFTWARE\\Microsoft\\MMC\\SnapIns"));
+
+ // Copy keyname into buffer.
+ _tcscat(szKeyBuf, _T("\\"));
+ _tcscat(szKeyBuf, pszCLSID);
+
+ // Delete the CLSID Key - CLSID\{...}
+ LONG lResult = recursiveDeleteKey(HKEY_LOCAL_MACHINE, szKeyBuf);
+ assert((lResult == ERROR_SUCCESS) ||
+ (lResult == ERROR_FILE_NOT_FOUND)) ; // Subkey may not exist.
+
+ //Uncomment following for loop to unregister all extendable node types
+ //Note that if a snap-in's extendable node types are unregistered,
+ //any extension snap-ins for these node types will have to be re-registered
+ //in order to rebuild their entries under the SOFTWARE\Microsoft\MMC\NodeTypes key
+
+/*
+ // Unregister each of the node types in _ExtendableNodes as an extendable node
+ // Note that this snap-in does not register any extendable node types
+
+ EXTENSION_NODE *pNode;
+ LPOLESTR wszExtendCLSID = NULL;
+
+ for (pNode = &(_ExtendableNodes[0]);*pNode->szDescription;pNode++)
+ {
+ hr = StringFromCLSID(pNode->GUID, &wszExtendCLSID);
+ MAKE_TSTRPTR_FROMWIDE(pszExtendCLSID, wszExtendCLSID);
+
+ // Load the buffer with the Snap-In Location
+ _tcscpy(szKeyBuf, _T("SOFTWARE\\Microsoft\\MMC\\NodeTypes\\"));
+ // Copy keyname into buffer.
+ _tcscat(szKeyBuf, pszExtendCLSID);
+ recursiveDeleteKey(HKEY_LOCAL_MACHINE, szKeyBuf);
+ CoTaskMemFree(wszExtendCLSID);
+ }
+
+*/
+
+ // free the memory
+ CoTaskMemFree(wszCLSID);
+
+ return S_OK;
+}
+
+//
+// Delete a key and all of its descendents.
+//
+LONG recursiveDeleteKey(HKEY hKeyParent, // Parent of key to delete
+ const _TCHAR* lpszKeyChild) // Key to delete
+{
+ // Open the child.
+ HKEY hKeyChild ;
+ LONG lRes = RegOpenKeyEx(hKeyParent, lpszKeyChild, 0,
+ KEY_ALL_ACCESS, &hKeyChild) ;
+ if (lRes != ERROR_SUCCESS)
+ {
+ return lRes ;
+ }
+
+ // Enumerate all of the decendents of this child.
+ FILETIME time ;
+ _TCHAR szBuffer[256] ;
+ DWORD dwSize = 256 ;
+ while (RegEnumKeyEx(hKeyChild, 0, szBuffer, &dwSize, NULL,
+ NULL, NULL, &time) == S_OK)
+ {
+ // Delete the decendents of this child.
+ lRes = recursiveDeleteKey(hKeyChild, szBuffer) ;
+ if (lRes != ERROR_SUCCESS)
+ {
+ // Cleanup before exiting.
+ RegCloseKey(hKeyChild) ;
+ return lRes;
+ }
+ dwSize = 256 ;
+ }
+
+ // Close the child.
+ RegCloseKey(hKeyChild) ;
+
+ // Delete this child.
+ return RegDeleteKey(hKeyParent, lpszKeyChild) ;
+}
+
+//
+// Create a key and set its value.
+// - This helper function was borrowed and modifed from
+// Kraig Brockschmidt's book Inside OLE.
+//
+BOOL setKeyAndValue(const _TCHAR* szKey,
+ const _TCHAR* szSubkey,
+ const _TCHAR* szValue)
+{
+ HKEY hKey;
+ _TCHAR szKeyBuf[1024] ;
+
+ // Copy keyname into buffer.
+ _tcscpy(szKeyBuf, szKey) ;
+
+ // Add subkey name to buffer.
+ if (szSubkey != NULL)
+ {
+ _tcscat(szKeyBuf, _T("\\")) ;
+ _tcscat(szKeyBuf, szSubkey ) ;
+ }
+
+ // Create and open key and subkey.
+ long lResult = RegCreateKeyEx(HKEY_CLASSES_ROOT ,
+ szKeyBuf,
+ 0, NULL, REG_OPTION_NON_VOLATILE,
+ KEY_ALL_ACCESS, NULL,
+ &hKey, NULL) ;
+ if (lResult != ERROR_SUCCESS)
+ {
+ return FALSE ;
+ }
+
+ // Set the Value.
+ if (szValue != NULL)
+ {
+ RegSetValueEx(hKey, NULL, 0, REG_SZ,
+ (BYTE *)szValue,
+ (_tcslen(szValue)+1)*sizeof(_TCHAR)) ;
+ }
+
+ RegCloseKey(hKey) ;
+ return TRUE ;
+}
+
+//
+// Open a key value and set it
+//
+BOOL setValue(const _TCHAR* szKey,
+ const _TCHAR* szValueName,
+ const _TCHAR* szValue)
+{
+ HKEY hKey;
+ _TCHAR szKeyBuf[1024] ;
+
+ // Copy keyname into buffer.
+ _tcscpy(szKeyBuf, szKey) ;
+
+ // Create and open key and subkey.
+ long lResult = RegCreateKeyEx(HKEY_CLASSES_ROOT ,
+ szKeyBuf,
+ 0, NULL, REG_OPTION_NON_VOLATILE,
+ KEY_ALL_ACCESS, NULL,
+ &hKey, NULL) ;
+ if (lResult != ERROR_SUCCESS)
+ {
+ return FALSE ;
+ }
+
+ // Set the Value.
+ if (szValue != NULL)
+ {
+ RegSetValueEx(hKey, szValueName, 0, REG_SZ,
+ (BYTE *)szValue,
+ (_tcslen(szValue)+1)*sizeof(_TCHAR)) ;
+ }
+
+ RegCloseKey(hKey) ;
+ return TRUE ;
+}
+
+
+//
+// Create a key and set its value.
+// - This helper function was borrowed and modifed from
+// Kraig Brockschmidt's book Inside OLE.
+//
+BOOL setSnapInKeyAndValue(const _TCHAR* szKey,
+ const _TCHAR* szSubkey,
+ const _TCHAR* szName,
+ const _TCHAR* szValue)
+{
+ HKEY hKey;
+ _TCHAR szKeyBuf[1024] ;
+
+ // Load the buffer with the Snap-In Location
+ _tcscpy(szKeyBuf, _T("SOFTWARE\\Microsoft\\MMC\\SnapIns"));
+
+ // Copy keyname into buffer.
+ _tcscat(szKeyBuf, _T("\\")) ;
+ _tcscat(szKeyBuf, szKey) ;
+
+ // Add subkey name to buffer.
+ if (szSubkey != NULL)
+ {
+ _tcscat(szKeyBuf, _T("\\")) ;
+ _tcscat(szKeyBuf, szSubkey ) ;
+ }
+
+ // Create and open key and subkey.
+ long lResult = RegCreateKeyEx(HKEY_LOCAL_MACHINE ,
+ szKeyBuf,
+ 0, NULL, REG_OPTION_NON_VOLATILE,
+ KEY_ALL_ACCESS, NULL,
+ &hKey, NULL) ;
+ if (lResult != ERROR_SUCCESS)
+ {
+ return FALSE ;
+ }
+
+ // Set the Value.
+ if (szValue != NULL)
+ {
+ RegSetValueEx(hKey, szName, 0, REG_SZ,
+ (BYTE *)szValue,
+ (_tcslen(szValue)+1)*sizeof(_TCHAR)) ;
+ }
+
+ RegCloseKey(hKey) ;
+ return TRUE ;
+}
+
+BOOL setSnapInExtensionNode(const _TCHAR* szSnapID,
+ const _TCHAR* szNodeID,
+ const _TCHAR* szDescription)
+{
+ HKEY hKey;
+ _TCHAR szSnapNodeKeyBuf[1024] ;
+ _TCHAR szMMCNodeKeyBuf[1024];
+
+ // Load the buffer with the Snap-In Location
+ _tcscpy(szSnapNodeKeyBuf, _T("SOFTWARE\\Microsoft\\MMC\\SnapIns\\"));
+ // add in the clisid into buffer.
+ _tcscat(szSnapNodeKeyBuf, szSnapID) ;
+ _tcscat(szSnapNodeKeyBuf, _T("\\NodeTypes\\"));
+ _tcscat(szSnapNodeKeyBuf, szNodeID) ;
+
+ // Load the buffer with the NodeTypes Location
+ _tcscpy(szMMCNodeKeyBuf, _T("SOFTWARE\\Microsoft\\MMC\\NodeTypes\\"));
+ _tcscat(szMMCNodeKeyBuf, szNodeID) ;
+
+ // Create and open the Snapin Key.
+ long lResult = RegCreateKeyEx(HKEY_LOCAL_MACHINE ,
+ szSnapNodeKeyBuf,
+ 0, NULL, REG_OPTION_NON_VOLATILE,
+ KEY_ALL_ACCESS, NULL,
+ &hKey, NULL) ;
+ if (lResult != ERROR_SUCCESS)
+ {
+ return FALSE ;
+ }
+
+ // Set the Value.
+ if (szDescription != NULL)
+ {
+ RegSetValueEx(hKey, NULL, 0, REG_SZ,
+ (BYTE *)szDescription,
+ (_tcslen(szDescription)+1)*sizeof(_TCHAR)) ;
+ }
+
+ RegCloseKey(hKey) ;
+
+ // Create and open the NodeTypes Key.
+ lResult = RegCreateKeyEx(HKEY_LOCAL_MACHINE ,
+ szMMCNodeKeyBuf,
+ 0, NULL, REG_OPTION_NON_VOLATILE,
+ KEY_ALL_ACCESS, NULL,
+ &hKey, NULL) ;
+ if (lResult != ERROR_SUCCESS)
+ {
+ return FALSE ;
+ }
+
+ // Set the Value.
+ if (szDescription != NULL)
+ {
+ RegSetValueEx(hKey, NULL, 0, REG_SZ,
+ (BYTE *)szDescription,
+ (_tcslen(szDescription)+1)*sizeof(_TCHAR)) ;
+ }
+
+ RegCloseKey(hKey) ;
+
+ return TRUE ;
+}
--- /dev/null
+//==============================================================;
+//
+// This source code is only intended as a supplement to existing Microsoft documentation.
+//
+//
+//
+//
+// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF ANY
+// KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
+// IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A PARTICULAR
+// PURPOSE.
+//
+// Copyright (C) 1999 - 2001 Microsoft Corporation. All Rights Reserved.
+//
+//
+//
+//==============================================================;
+
+#ifndef __Registry_H__
+#define __Registry_H__
+
+#include <tchar.h>
+
+// This function will register a component in the Registry.
+// The component calls this function from its DllRegisterServer function.
+HRESULT RegisterServer(HMODULE hModule,
+ const CLSID& clsid,
+ const _TCHAR* szFriendlyName) ;
+
+// This function will unregister a component. Components
+// call this function from their DllUnregisterServer function.
+HRESULT UnregisterServer(const CLSID& clsid) ;
+
+
+// This function will register a Snap-In component. Components
+// call this function from their DllRegisterServer function.
+HRESULT RegisterSnapin(const CLSID& clsid, // Class ID
+ const _TCHAR* szNameString); // NameString
+
+
+
+HRESULT UnregisterSnapin(const CLSID& clsid); // Class ID
+
+#endif
\ No newline at end of file
--- /dev/null
+//{{NO_DEPENDENCIES}}
+// Microsoft Developer Studio generated include file.
+// Used by isapi_gui.Rc
+//
+#define IDS_HELPFILE 1
+#define IDS_SNAPINDESC 2
+#define IDS_NAME 3
+#define IDS_THIS_WEB_INSTANCE 4
+#define IDS_SERVER_DEFAULT 5
+#define IDS_SNAPINNAME 6
+#define IDS_PROGRAM_DEFAULT 7
+#define IDS_ABOUTNAME 9
+#define IDD_PROPPAGE_LARGE 10
+#define IDS_PST_TAB_NAME 10
+#define IDD_PROPPAGE_DIRECTIVE 10
+#define IDD_PROPPAGE 10
+#define IDI_ICON1 108
+#define IDI_PSI_ROCKET 114
+#define IDR_SMICONS 120
+#define IDR_LGICONS 121
+#define IDB_SMOPEN 124
+#define IDB_SMBMP 125
+#define IDB_LGBMP 126
+#define IDC_PROPS 1006
+#define IDC_EDIT2 1008
+#define IDC_COMBO3 1009
+#define IDC_ValueBox 1009
+#define IDC_ValueEdit 1014
+#define IDC_InheritedFrom 1015
+#define IDC_MoreInfo 1016
+#define IDC_NAME 1018
+#define IDC_InheritedFromStatic 1019
+#define IDC_Delete 1020
+#define IDC_Refresh 1021
+#define EDIT1 40027
+#define EDIT2 40028
+#define EDIT3 40029
+#define EDIT4 40030
+#define COMBO1 40031
+
+// Next default values for new objects
+//
+#ifdef APSTUDIO_INVOKED
+#ifndef APSTUDIO_READONLY_SYMBOLS
+#define _APS_NEXT_RESOURCE_VALUE 127
+#define _APS_NEXT_COMMAND_VALUE 40032
+#define _APS_NEXT_CONTROL_VALUE 1023
+#define _APS_NEXT_SYMED_VALUE 101
+#endif
+#endif