clprefskeyservers.c

来自「PGP8.0源码 请认真阅读您的文件包然后写出其具体功能」· C语言 代码 · 共 1,589 行 · 第 1/3 页

C
1,589
字号
/*____________________________________________________________________________
	Copyright (C) 2002 PGP Corporation
	All rights reserved.
	
	CLprefsKeyservers.c - handle PGP keyserver preferences dialogs

	$Id: CLprefsKeyservers.c,v 1.24 2002/10/29 18:30:41 pbj Exp $
____________________________________________________________________________*/
#include "pgpPFLConfig.h"

// project header files
#include "PGPclx.h"
#include "CLprefs.h"
#include "UTF8Edit.h"

// constant definitions
#define TREEOFFSETLEFT		8
#define BUTTONOFFSETX		10
#define BUTTONOFFSETY		10

#define DOMAINLISTWIDTH		53
#define CHECKLISTWIDTH		48

#define DELAYTIMER			543

#define PGPKeyserverHTTP	0
#define PGPKeyserverLDAP	1
#define PGPKeyserverLDAPS	2
//#define PGPLDAP			3
//#define PGPLDAPS			4
#define X509LDAP			3
#define X509LDAPS			4

// typedefs
typedef struct {
	PPREFSDLGSTRUCT			ppds;
	HWND					hwndTree;
	BOOL					bEdit;
	CHAR					szServer[256];
	PGPUInt32				iType;
	PGPUInt16				iPort;
	CHAR					szKeyStoreDN[kMaxKeyStoreDNLength];
	PGPKeyServerProtocol	protocol;
	CHAR					szKeyIDAuth[kPGPMaxKeyIDStringSize];
	PGPPublicKeyAlgorithm	authAlg;
	CHAR					szUserIDAuth[kPGPMaxUserIDSize +1];
	CHAR					szDomain[256];
	BOOL					bListed;
	BOOL					bRoot;
	VOID*					pOrigStruct;
} KEYSERVERSTRUCT, *PKEYSERVERSTRUCT;


// external globals
extern HINSTANCE	g_hInst;
extern HIMAGELIST	g_hilClientLib;


static DWORD aServerIds[] = {			// Help IDs
	IDC_NEWKEYSERVER,		IDH_PGPCLPREF_CREATESERVER,
	IDC_REMOVEKEYSERVER,	IDH_PGPCLPREF_REMOVESERVER,
	IDC_EDITKEYSERVER,		IDH_PGPCLPREF_EDITSERVER,
	IDC_SETASROOT,			IDH_PGPCLPREF_SETROOTSERVER,
	IDC_MOVEUP,				IDH_PGPCLPREF_MOVESERVERUP,
	IDC_MOVEDOWN,			IDH_PGPCLPREF_MOVESERVERDOWN,
	IDC_SYNCONUNKNOWN,		IDH_PGPCLPREF_SYNCONUNKNOWNKEYS,
	IDC_SYNCONADDNAME,		IDH_PGPCLPREF_SYNCONADDNAME,
	IDC_SYNCONKEYSIGN,		IDH_PGPCLPREF_SYNCONSIGN,
	IDC_SYNCONREVOKE,		IDH_PGPCLPREF_SYNCONREVOKE,
	IDC_SYNCONVERIFY,		IDH_PGPCLPREF_SYNCONVERIFY,
	IDC_KSTREELIST,			IDH_PGPCLPREF_SERVERLIST,
	IDC_SYNCONSTATICTEXT,	-1,
	0,0
};

static DWORD aEditServerIds[] = {		// Help IDs
	IDC_TYPE,				IDH_PGPCLPREF_SERVERTYPE,
    IDC_SERVERNAME,			IDH_PGPCLPREF_SERVERNAME, 
	IDC_PORT,				IDH_PGPCLPREF_SERVERPORT,
	IDC_SERVERBASEDN,		IDH_PGPCLPREF_SERVERBASEDN,
	IDC_SERVERKEY,			IDH_PGPCLPREF_SERVERAUTHKEY,
	IDC_ANYDOMAIN,			IDH_PGPCLPREF_SERVERNODOMAIN,
    IDC_DOMAIN,				IDH_PGPCLPREF_SERVERDOMAIN, 
    IDC_SPECIFIEDDOMAIN,	IDH_PGPCLPREF_SERVERDOMAIN, 
    IDC_LISTED,				IDH_PGPCLPREF_SERVERLISTED, 
    0,0 
}; 


//	_____________________________________________________
//
//  concatenate protocol and server names

static VOID
sURLfromInfo (
		PGPKeyServerProtocol	protocol, 
		LPSTR					szServer, 
		PGPUInt16				iPort, 
		LPSTR					szURL)
{
	switch (protocol) {
	case kPGPKeyServerProtocol_LDAP :	lstrcpy (szURL, "ldap://"); break;
	case kPGPKeyServerProtocol_LDAPS :	lstrcpy (szURL, "ldaps://"); break;
	case kPGPKeyServerProtocol_HTTPS :	lstrcpy (szURL, "https://"); break;
	default :							lstrcpy (szURL, "http://"); break;
	}

	lstrcat (szURL, szServer);

	if (iPort != 0) 
	{
		CHAR szPort[8];
		wsprintf (szPort, ":%i", iPort);
		lstrcat (szURL, szPort);
	}
}

//	_____________________________________________________
//
//  put data for one keyserver into treelist

static HTLITEM
sSetOneKSItem (
		HWND				hwndTree, 
		PKEYSERVERSTRUCT	pkss)
{
	TL_TREEITEM		tlI;
	TL_LISTITEM		tlL;
	TL_INSERTSTRUCT tlIns;
	HTLITEM			hTNew;
	CHAR			sz[256];

	sURLfromInfo (pkss->protocol, pkss->szServer, pkss->iPort, sz);

	tlI.hItem = NULL;
	tlI.mask = TLIF_TEXT | TLIF_IMAGE | TLIF_STATE | TLIF_PARAM;
	tlI.stateMask = TLIS_BOLD;
	if (pkss->bRoot) 
		tlI.state = TLIS_BOLD;
	else
		tlI.state = 0;
	tlI.pszText = sz;
	tlI.cchTextMax = lstrlen (sz);
	tlI.iImage = IDX_SERVER;
	tlI.iSelectedImage = IDX_SERVER;
	tlI.lParam = (LPARAM)pkss;

	tlIns.item = tlI;
	tlIns.hInsertAfter = (HTLITEM)TLI_LAST;
	tlIns.hParent = NULL;
	hTNew = TreeList_InsertItem (hwndTree, &tlIns);

	if (lstrlen (pkss->szDomain))
		tlL.pszText = pkss->szDomain;
	else 
		tlL.pszText = NULL;
	tlL.hItem = hTNew;
	tlL.stateMask = TLIS_VISIBLE;
	tlL.iSubItem = 1;
	tlL.mask = TLIF_DATAVALUE | TLIF_TEXT | TLIF_STATE;
	tlL.state = TLIS_VISIBLE;
	tlL.lDataValue = IDX_WORLDDOMAIN;

	TreeList_SetListItem (hwndTree, &tlL, FALSE);

	tlL.pszText = NULL;
	tlL.hItem = hTNew;
	tlL.stateMask = TLIS_VISIBLE;
	tlL.iSubItem = 2;
	tlL.mask = TLIF_DATAVALUE | TLIF_STATE;
	tlL.state = TLIS_VISIBLE;

	if (pkss->bListed) tlL.lDataValue = IDX_GREENDOT;
	else tlL.lDataValue = IDX_GREYDOT;

	TreeList_SetListItem (hwndTree, &tlL, FALSE);

	return hTNew;
}

//	_____________________________________________________
//
//  populate keyserver treelist with data from preferences

static INT
sFillTreeList (
		PPREFSDLGSTRUCT ppds)
{
	PGPKeyServerEntry*	keyserverList	= NULL;
	PGPKeyDBObjRef		key;
	PGPUInt32			u, u2;
	PGPError			err;
	PKEYSERVERSTRUCT	pkss;
	PGPKeyID			keyid;
	PGPPrefRef			prefref;

	// load keyserverprefs
	prefref = CLGetPrefRef (ppds);
	err = PGPGetKeyServerPrefs (prefref, 
				&keyserverList, &ppds->ks.uNumberOfServers);

	if (IsPGPError (err)) 
		ppds->ks.uNumberOfServers = 0;

	for (u=0; u<ppds->ks.uNumberOfServers; u++) 
	{
		pkss = clAlloc (sizeof(KEYSERVERSTRUCT));
		if (pkss) 
		{
			pkss->ppds		= ppds;
			pkss->hwndTree	= ppds->ks.hwndTree;
			pkss->bEdit		= FALSE;
			lstrcpy (pkss->szServer, keyserverList[u].serverDNS);
			pkss->iType		= keyserverList[u].type;
			pkss->iPort		= keyserverList[u].serverPort;
			lstrcpy (pkss->szKeyStoreDN, keyserverList[u].keystoredn);
			pkss->protocol	= keyserverList[u].protocol;
			lstrcpy (pkss->szDomain, keyserverList[u].domain);
			pkss->bListed	= (keyserverList[u].flags & kKeyServerListed);
			pkss->authAlg	= keyserverList[u].authAlg;
			pkss->bRoot		= (keyserverList[u].flags & kKeyServerIsRoot);

			// get auth key userid
			pkss->szUserIDAuth[0] = '\0';
			if ((pkss->authAlg != kPGPPublicKeyAlgorithm_Invalid) &&
					keyserverList[u].authKeyIDString[0]) 
			{
				lstrcpy (pkss->szKeyIDAuth, 
						keyserverList[u].authKeyIDString);
				err = PGPNewKeyIDFromString (
						keyserverList[u].authKeyIDString, 
						pkss->authAlg, &keyid);
				if (IsntPGPError (err)) 
				{
					err = PGPFindKeyByKeyID (ppds->keydbMain, &keyid, &key);
					if (IsntPGPError (err)) 
					{
						PGPclGetPrimaryUserIDNameUTF8 (key, 
								pkss->szUserIDAuth, 
								sizeof(pkss->szUserIDAuth), &u2);
					}
					else 
					{
						lstrcpy (pkss->szUserIDAuth, 
								keyserverList[u].authKeyIDString);
					}
				}
			}
			if (pkss->szUserIDAuth[0] == '\0') 
			{
				LoadString (g_hInst, IDS_UNKNOWNKEY, pkss->szUserIDAuth, 
						sizeof(pkss->szUserIDAuth));
			}

			sSetOneKSItem (ppds->ks.hwndTree, pkss); 
		}
	}

	if (keyserverList) 
		PGPFreeKeyServerList(keyserverList);

	return 0;
}


//	_____________________________________________________
//
//  add columns to treelist

static BOOL 
sAddColumns (
		HWND hwndTree, 
		INT iWidth) 
{
	TL_COLUMN tlc;
	CHAR sz[64];

	TreeList_DeleteAllColumns (hwndTree);

	tlc.mask = TLCF_FMT | TLCF_WIDTH | TLCF_TEXT | 
				TLCF_SUBITEM | TLCF_DATATYPE | TLCF_DATAMAX |
				TLCF_MOUSENOTIFY;
	tlc.pszText = sz;

	tlc.iSubItem = 0;
	tlc.fmt = TLCFMT_LEFT;
	tlc.iDataType = TLC_DATASTRING;
	tlc.cx = iWidth - DOMAINLISTWIDTH - CHECKLISTWIDTH - 20;
	tlc.bMouseNotify = FALSE;
	LoadString (g_hInst, IDS_SERVER, sz, sizeof(sz));
	TreeList_InsertColumn (hwndTree, 0, &tlc);

	tlc.fmt = TLCFMT_IMAGE;
	tlc.iDataType = TLC_DATALONG;
	tlc.cx = DOMAINLISTWIDTH;
	tlc.bMouseNotify = FALSE;
	LoadString (g_hInst, IDS_DOMAIN, sz, sizeof(sz));
	TreeList_InsertColumn (hwndTree, 1, &tlc);

	tlc.fmt = TLCFMT_IMAGE;
	tlc.iDataType = TLC_DATALONG;
	tlc.cx = CHECKLISTWIDTH;
	tlc.bMouseNotify = TRUE;
	LoadString (g_hInst, IDS_LISTED, sz, sizeof(sz));
	TreeList_InsertColumn (hwndTree, 2, &tlc);

	return TRUE;
}


//	_____________________________________________________
//
//  create new treelist control for keyserver prefs

static HWND
sCreateKeyserverTreeList (
		HWND			hwndParent,
		PPREFSDLGSTRUCT ppds)
{
	RECT rc;
	INT iwidth, iheight, itop;
	POINT pt;

	// Ensure that the common control DLL is loaded.
	InitCommonControls ();

	// Ensure that the custom control DLL is loaded.
	InitTreeListControl ();

	// initialize flags
	ppds->ks.iSelectedType	= IDX_NONE;
	ppds->ks.bSelectedRoot	= FALSE;
	ppds->ks.bLastInList	= TRUE;
	ppds->ks.bFirstInList	= TRUE;

	// create tree view window
	GetWindowRect (GetDlgItem (hwndParent, IDC_NEWKEYSERVER), &rc);
	pt.x = rc.left;
	pt.y = rc.top;
	ScreenToClient (hwndParent, &pt);
	itop = pt.y;
	iwidth = pt.x - BUTTONOFFSETX - TREEOFFSETLEFT;

	GetWindowRect (GetDlgItem (hwndParent, IDC_SYNCONSTATICTEXT), &rc);
	pt.x = rc.left;
	pt.y = rc.top;
	ScreenToClient (hwndParent, &pt);
	iheight = pt.y - BUTTONOFFSETY - itop;

	GetClientRect (hwndParent, &rc);

	ppds->ks.hwndTree = CreateWindowEx (WS_EX_CLIENTEDGE, WC_TREELIST, "",
			WS_VISIBLE | WS_CHILD | WS_BORDER | WS_TABSTOP | WS_GROUP |
			TLS_AUTOSCROLL | TLS_SINGLESELECT | 
			TLS_SHOWSELECTIONALWAYS | TLS_USEDEFAULTGUIFONT,
			TREEOFFSETLEFT, itop, iwidth, iheight,
			hwndParent, (HMENU)IDC_KSTREELIST, g_hInst, NULL);

	if (ppds->ks.hwndTree == NULL) 
		return NULL;

	// Associate the image list with the tree view control.
	TreeList_SetImageList (ppds->ks.hwndTree, g_hilClientLib);
	sAddColumns (ppds->ks.hwndTree, iwidth);
	sFillTreeList (ppds);

	return ppds->ks.hwndTree;
}

//	_____________________________________________________
//
//  destroy treelist control for keyserver prefs

static INT
sDestroyKeyserverTreeList (
		HWND	hwndTree) 
{
	HTLITEM		hTServer;
	TL_TREEITEM tlI;

	// free all KEYSERVERSTRUCT structures
	hTServer = TreeList_GetFirstItem (hwndTree);
	while (hTServer) 
	{
		tlI.hItem = hTServer;
		tlI.mask = TLIF_NEXTHANDLE | TLIF_PARAM;
		TreeList_GetItem (hwndTree, &tlI);

		clFree ((VOID*)(tlI.lParam));

		hTServer = tlI.hItem;
	}

	// close treelist
	SendMessage (hwndTree, WM_CLOSE, 0, 0);
	return 0;
}

//	_____________________________________________________
//
//  check if specified server is already in list

static BOOL
sIsThisServerAlreadyInList (
		PKEYSERVERSTRUCT	pkssThis)
{
	TL_TREEITEM			tlI;
	HTLITEM				hTServer;
	INT					iServerCount;
	PKEYSERVERSTRUCT	pkss;

	// count number of servers
	iServerCount = 0;
	hTServer = TreeList_GetFirstItem (pkssThis->hwndTree);
	while (hTServer) 
	{
		++iServerCount;
		tlI.hItem = hTServer;
		tlI.mask = TLIF_NEXTHANDLE;
		TreeList_GetItem (pkssThis->hwndTree, &tlI);
		hTServer = tlI.hItem;
	}

	hTServer = TreeList_GetFirstItem (pkssThis->hwndTree);
	while (hTServer) 
	{
		// get server structure
		tlI.hItem = hTServer;
		tlI.mask = TLIF_PARAM | TLIF_NEXTHANDLE;
		TreeList_GetItem (pkssThis->hwndTree, &tlI);

		pkss = (PKEYSERVERSTRUCT)(tlI.lParam);

		if (pkss != (PKEYSERVERSTRUCT)pkssThis->pOrigStruct) 
		{
			if (!lstrcmpi (pkss->szServer, pkssThis->szServer)) 
			{
				if (pkss->protocol == pkssThis->protocol) 
				{
					if (pkss->iPort == pkssThis->iPort) 
						return TRUE;
				}
			}
		}

		// step to next server
		hTServer = tlI.hItem;
	}

	return FALSE;
}

//	_____________________________________________________
//
//  find out if there are any domain-less servers among those
//  which are not selected.

static BOOL
sIsThisTheOnlyWorldServer (
		PPREFSDLGSTRUCT	ppds)
{
	HTLITEM				hTServer;
	TL_TREEITEM			tlI;
	PKEYSERVERSTRUCT	pkss;

	// is the selected server a "world" server?
	tlI.hItem = ppds->ks.hTSelected;
	tlI.mask = TLIF_PARAM;
	TreeList_GetItem (ppds->ks.hwndTree, &tlI);
	pkss = (PKEYSERVERSTRUCT)tlI.lParam;

	// if server has a domain, then it's not a "world" server.
	if (pkss->szDomain[0]) 
		return FALSE;

	// interate through tree
	hTServer = TreeList_GetFirstItem (ppds->ks.hwndTree);
	while (hTServer) 
	{
		if (hTServer != ppds->ks.hTSelected) 
		{
			// get keyserver structure
			tlI.hItem = hTServer;
			tlI.mask = TLIF_PARAM;
			TreeList_GetItem (ppds->ks.hwndTree, &tlI);

			pkss = (PKEYSERVERSTRUCT)tlI.lParam;

			// if this server doesn't have a domain, then the
			// selected server isn't the last "world" server
			if (pkss->szDomain[0] == 0)
				return FALSE;
		}

		// get next server
		tlI.hItem = hTServer;
		tlI.mask = TLIF_NEXTHANDLE;
		TreeList_GetItem (ppds->ks.hwndTree, &tlI);

		hTServer = tlI.hItem;
	}
	
	// didn't find any other "world" servers
	return TRUE;
}

//	___________________________________________
//
//  New/Edit Keyserver Dialog Message procedure

static BOOL CALLBACK 
sEditServerDlgProc (
		HWND	hDlg, 
		UINT	uMsg, 
		WPARAM	wParam,
		LPARAM	lParam) 
{
	PKEYSERVERSTRUCT	pkss;
	CHAR				sz[256];
	LPSTR				p;
	INT					iSelected;

	switch (uMsg) {

	case WM_INITDIALOG :
		SetWindowLong (hDlg, GWL_USERDATA, lParam);
		pkss = (PKEYSERVERSTRUCT)lParam;
		if (pkss->bEdit) 
		{
			LoadString (g_hInst, IDS_EDITSERVERTITLE, sz, sizeof(sz));

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?