OSDN Git Service

Add routines for SSL root CA certificates.
authors_kawamoto <s_kawamoto@users.sourceforge.jp>
Sun, 13 Nov 2011 17:14:34 +0000 (02:14 +0900)
committers_kawamoto <s_kawamoto@users.sourceforge.jp>
Sun, 13 Nov 2011 17:14:34 +0000 (02:14 +0900)
Fix bugs of routines for IPv6.

FFFTP_Eng_Release/FFFTP.exe
Release/FFFTP.exe
misc.c
socketwrapper.c
socketwrapper.h

index 1367f2a..819df2f 100644 (file)
Binary files a/FFFTP_Eng_Release/FFFTP.exe and b/FFFTP_Eng_Release/FFFTP.exe differ
index 4d88b3e..909b0c0 100644 (file)
Binary files a/Release/FFFTP.exe and b/Release/FFFTP.exe differ
diff --git a/misc.c b/misc.c
index 58700a7..d064173 100644 (file)
--- a/misc.c
+++ b/misc.c
@@ -987,9 +987,23 @@ int SplitUNCpath(char *unc, char *Host, char *Path, char *File, char *User, char
                        strncpy(User, Tmp, USER_NAME_LEN);\r
        }\r
 \r
+       // IPv6対応\r
+       if((Pos2 = _mbschr(Pos1, '[')) != NULL && Pos2 < _mbschr(Pos1, ':'))\r
+       {\r
+               Pos1 = Pos2 + 1;\r
+               if((Pos2 = _mbschr(Pos2, ']')) != NULL)\r
+               {\r
+                       memcpy(Host, Pos1, min1(Pos2-Pos1, HOST_ADRS_LEN));\r
+                       Pos1 = Pos2 + 1;\r
+               }\r
+       }\r
+\r
        if((Pos2 = _mbschr(Pos1, ':')) != NULL)\r
        {\r
-               memcpy(Host, Pos1, min1(Pos2-Pos1, HOST_ADRS_LEN));\r
+               // IPv6対応\r
+//             memcpy(Host, Pos1, min1(Pos2-Pos1, HOST_ADRS_LEN));\r
+               if(strlen(Host) == 0)\r
+                       memcpy(Host, Pos1, min1(Pos2-Pos1, HOST_ADRS_LEN));\r
                Pos2++;\r
                if(IsDigit(*Pos2))\r
                {\r
@@ -1006,13 +1020,19 @@ int SplitUNCpath(char *unc, char *Host, char *Path, char *File, char *User, char
        }\r
        else if((Pos2 = _mbschr(Pos1, '/')) != NULL)\r
        {\r
-               memcpy(Host, Pos1, min1(Pos2-Pos1, HOST_ADRS_LEN));\r
+               // IPv6対応\r
+//             memcpy(Host, Pos1, min1(Pos2-Pos1, HOST_ADRS_LEN));\r
+               if(strlen(Host) == 0)\r
+                       memcpy(Host, Pos1, min1(Pos2-Pos1, HOST_ADRS_LEN));\r
                RemoveFileName(Pos2, Path);\r
                strncpy(File, GetFileName(Pos2), FMAX_PATH);\r
        }\r
        else\r
        {\r
-               strncpy(Host, Pos1, HOST_ADRS_LEN);\r
+               // IPv6対応\r
+//             strncpy(Host, Pos1, HOST_ADRS_LEN);\r
+               if(strlen(Host) == 0)\r
+                       strncpy(Host, Pos1, HOST_ADRS_LEN);\r
        }\r
 \r
        Sts = FFFTP_FAIL;\r
index d5a3d10..8aac220 100644 (file)
@@ -32,14 +32,17 @@ typedef X509* (__cdecl* _SSL_get_peer_certificate)(const SSL*);
 typedef long (__cdecl* _SSL_get_verify_result)(const SSL*);\r
 typedef SSL_SESSION* (__cdecl* _SSL_get_session)(SSL*);\r
 typedef int (__cdecl* _SSL_set_session)(SSL*, SSL_SESSION*);\r
+typedef int (__cdecl* _SSL_CTX_use_certificate)(SSL_CTX*, X509*);\r
 typedef BIO_METHOD* (__cdecl* _BIO_s_mem)();\r
 typedef BIO* (__cdecl* _BIO_new)(BIO_METHOD*);\r
 typedef int (__cdecl* _BIO_free)(BIO*);\r
+typedef BIO* (__cdecl* _BIO_new_mem_buf)(void*, int);\r
 typedef long (__cdecl* _BIO_ctrl)(BIO*, int, long, void*);\r
 typedef void (__cdecl* _X509_free)(X509*);\r
 typedef int (__cdecl* _X509_print_ex)(BIO*, X509*, unsigned long, unsigned long);\r
 typedef X509_NAME* (__cdecl* _X509_get_subject_name)(X509*);\r
 typedef int (__cdecl* _X509_NAME_print_ex)(BIO*, X509_NAME*, int, unsigned long);\r
+typedef X509* (__cdecl* _PEM_read_bio_X509)(BIO*, X509**, pem_password_cb*, void*);\r
 \r
 _SSL_load_error_strings p_SSL_load_error_strings;\r
 _SSL_library_init p_SSL_library_init;\r
@@ -61,14 +64,17 @@ _SSL_get_peer_certificate p_SSL_get_peer_certificate;
 _SSL_get_verify_result p_SSL_get_verify_result;\r
 _SSL_get_session p_SSL_get_session;\r
 _SSL_set_session p_SSL_set_session;\r
+_SSL_CTX_use_certificate p_SSL_CTX_use_certificate;\r
 _BIO_s_mem p_BIO_s_mem;\r
 _BIO_new p_BIO_new;\r
 _BIO_free p_BIO_free;\r
+_BIO_new_mem_buf p_BIO_new_mem_buf;\r
 _BIO_ctrl p_BIO_ctrl;\r
 _X509_free p_X509_free;\r
 _X509_print_ex p_X509_print_ex;\r
 _X509_get_subject_name p_X509_get_subject_name;\r
 _X509_NAME_print_ex p_X509_NAME_print_ex;\r
+_PEM_read_bio_X509 p_PEM_read_bio_X509;\r
 \r
 #define MAX_SSL_SOCKET 16\r
 \r
@@ -93,6 +99,7 @@ BOOL __stdcall DefaultSSLConfirmCallback(BOOL* pbAborted, BOOL bVerified, LPCSTR
        return bVerified;\r
 }\r
 \r
+// OpenSSLを初期化\r
 BOOL LoadOpenSSL()\r
 {\r
        if(g_bOpenSSLLoaded)\r
@@ -106,8 +113,9 @@ BOOL LoadOpenSSL()
        RegisterTrustedModuleSHA1Hash("\x01\x32\x7A\xAE\x69\x26\xE6\x58\xC7\x63\x22\x1E\x53\x5A\x78\xBC\x61\xC7\xB5\xC1");\r
 #endif\r
        g_hOpenSSL = LoadLibrary("ssleay32.dll");\r
-       if(!g_hOpenSSL)\r
-               g_hOpenSSL = LoadLibrary("libssl32.dll");\r
+       // バージョン固定のためlibssl32.dllの読み込みは脆弱性の原因になり得るので廃止\r
+//     if(!g_hOpenSSL)\r
+//             g_hOpenSSL = LoadLibrary("libssl32.dll");\r
        if(!g_hOpenSSL\r
                || !(p_SSL_load_error_strings = (_SSL_load_error_strings)GetProcAddress(g_hOpenSSL, "SSL_load_error_strings"))\r
                || !(p_SSL_library_init = (_SSL_library_init)GetProcAddress(g_hOpenSSL, "SSL_library_init"))\r
@@ -128,7 +136,8 @@ BOOL LoadOpenSSL()
                || !(p_SSL_get_peer_certificate = (_SSL_get_peer_certificate)GetProcAddress(g_hOpenSSL, "SSL_get_peer_certificate"))\r
                || !(p_SSL_get_verify_result = (_SSL_get_verify_result)GetProcAddress(g_hOpenSSL, "SSL_get_verify_result"))\r
                || !(p_SSL_get_session = (_SSL_get_session)GetProcAddress(g_hOpenSSL, "SSL_get_session"))\r
-               || !(p_SSL_set_session = (_SSL_set_session)GetProcAddress(g_hOpenSSL, "SSL_set_session")))\r
+               || !(p_SSL_set_session = (_SSL_set_session)GetProcAddress(g_hOpenSSL, "SSL_set_session"))\r
+               || !(p_SSL_CTX_use_certificate = (_SSL_CTX_use_certificate)GetProcAddress(g_hOpenSSL, "SSL_CTX_use_certificate")))\r
        {\r
                if(g_hOpenSSL)\r
                        FreeLibrary(g_hOpenSSL);\r
@@ -140,11 +149,13 @@ BOOL LoadOpenSSL()
                || !(p_BIO_s_mem = (_BIO_s_mem)GetProcAddress(g_hOpenSSLCommon, "BIO_s_mem"))\r
                || !(p_BIO_new = (_BIO_new)GetProcAddress(g_hOpenSSLCommon, "BIO_new"))\r
                || !(p_BIO_free = (_BIO_free)GetProcAddress(g_hOpenSSLCommon, "BIO_free"))\r
+               || !(p_BIO_new_mem_buf = (_BIO_new_mem_buf)GetProcAddress(g_hOpenSSLCommon, "BIO_new_mem_buf"))\r
                || !(p_BIO_ctrl = (_BIO_ctrl)GetProcAddress(g_hOpenSSLCommon, "BIO_ctrl"))\r
                || !(p_X509_free = (_X509_free)GetProcAddress(g_hOpenSSLCommon, "X509_free"))\r
                || !(p_X509_print_ex = (_X509_print_ex)GetProcAddress(g_hOpenSSLCommon, "X509_print_ex"))\r
                || !(p_X509_get_subject_name = (_X509_get_subject_name)GetProcAddress(g_hOpenSSLCommon, "X509_get_subject_name"))\r
-               || !(p_X509_NAME_print_ex = (_X509_NAME_print_ex)GetProcAddress(g_hOpenSSLCommon, "X509_NAME_print_ex")))\r
+               || !(p_X509_NAME_print_ex = (_X509_NAME_print_ex)GetProcAddress(g_hOpenSSLCommon, "X509_NAME_print_ex"))\r
+               || !(p_PEM_read_bio_X509 = (_PEM_read_bio_X509)GetProcAddress(g_hOpenSSLCommon, "PEM_read_bio_X509")))\r
        {\r
                if(g_hOpenSSL)\r
                        FreeLibrary(g_hOpenSSL);\r
@@ -163,6 +174,7 @@ BOOL LoadOpenSSL()
        return TRUE;\r
 }\r
 \r
+// OpenSSLを解放\r
 void FreeOpenSSL()\r
 {\r
        int i;\r
@@ -190,6 +202,7 @@ void FreeOpenSSL()
        g_bOpenSSLLoaded = FALSE;\r
 }\r
 \r
+// OpenSSLが使用可能かどうか確認\r
 BOOL IsOpenSSLLoaded()\r
 {\r
        return g_bOpenSSLLoaded;\r
@@ -308,6 +321,37 @@ void SetSSLConfirmCallback(LPSSLCONFIRMCALLBACK pCallback)
        LeaveCriticalSection(&g_OpenSSLLock);\r
 }\r
 \r
+// SSLルート証明書を設定\r
+BOOL SetSSLRootCertificate(void* pData, DWORD Length)\r
+{\r
+       BOOL r;\r
+       BIO* pBIO;\r
+       X509* pX509;\r
+       if(!g_bOpenSSLLoaded)\r
+               return FALSE;\r
+       r = FALSE;\r
+       EnterCriticalSection(&g_OpenSSLLock);\r
+       if(!g_pOpenSSLCTX)\r
+               g_pOpenSSLCTX = p_SSL_CTX_new(p_SSLv23_method());\r
+       if(g_pOpenSSLCTX)\r
+       {\r
+               if(pBIO = p_BIO_new_mem_buf(pData, Length))\r
+               {\r
+                       if(pX509 = p_PEM_read_bio_X509(pBIO, NULL, NULL, NULL))\r
+                       {\r
+                               if(p_SSL_CTX_use_certificate(g_pOpenSSLCTX, pX509) == 1)\r
+                                       r = TRUE;\r
+                               p_X509_free(pX509);\r
+                       }\r
+                       p_BIO_free(pBIO);\r
+               }\r
+       }\r
+       LeaveCriticalSection(&g_OpenSSLLock);\r
+       return r;\r
+}\r
+\r
+// ワイルドカードの比較\r
+// 主にSSL証明書のCN確認用\r
 BOOL IsHostNameMatched(LPCSTR HostName, LPCSTR CommonName)\r
 {\r
        BOOL bResult;\r
@@ -333,6 +377,7 @@ BOOL IsHostNameMatched(LPCSTR HostName, LPCSTR CommonName)
        return bResult;\r
 }\r
 \r
+// SSLセッションを開始\r
 BOOL AttachSSL(SOCKET s, SOCKET parent, BOOL* pbAborted)\r
 {\r
        BOOL r;\r
@@ -420,6 +465,7 @@ BOOL AttachSSL(SOCKET s, SOCKET parent, BOOL* pbAborted)
        return r;\r
 }\r
 \r
+// SSLセッションを終了\r
 BOOL DetachSSL(SOCKET s)\r
 {\r
        BOOL r;\r
@@ -439,6 +485,8 @@ BOOL DetachSSL(SOCKET s)
        return r;\r
 }\r
 \r
+// SSLとしてマークされているか確認\r
+// マークされていればTRUEを返す\r
 BOOL IsSSLAttached(SOCKET s)\r
 {\r
        SSL** ppSSL;\r
@@ -467,6 +515,8 @@ int listenS(SOCKET s, int backlog)
        return listen(s, backlog);\r
 }\r
 \r
+// accept相当の関数\r
+// ただし初めからSSLのネゴシエーションを行う\r
 SOCKET acceptS(SOCKET s, struct sockaddr *addr, int *addrlen)\r
 {\r
        SOCKET r;\r
@@ -481,6 +531,8 @@ SOCKET acceptS(SOCKET s, struct sockaddr *addr, int *addrlen)
        return r;\r
 }\r
 \r
+// connect相当の関数\r
+// ただし初めからSSLのネゴシエーションを行う\r
 int connectS(SOCKET s, const struct sockaddr *name, int namelen)\r
 {\r
        int r;\r
@@ -492,12 +544,14 @@ int connectS(SOCKET s, const struct sockaddr *name, int namelen)
        return r;\r
 }\r
 \r
+// closesocket相当の関数\r
 int closesocketS(SOCKET s)\r
 {\r
        DetachSSL(s);\r
        return closesocket(s);\r
 }\r
 \r
+// send相当の関数\r
 int sendS(SOCKET s, const char * buf, int len, int flags)\r
 {\r
        SSL** ppSSL;\r
@@ -511,6 +565,7 @@ int sendS(SOCKET s, const char * buf, int len, int flags)
        return p_SSL_write(*ppSSL, buf, len);\r
 }\r
 \r
+// recv相当の関数\r
 int recvS(SOCKET s, char * buf, int len, int flags)\r
 {\r
        SSL** ppSSL;\r
index cfef1a2..b903e9f 100644 (file)
@@ -15,6 +15,7 @@ void FreeOpenSSL();
 BOOL IsOpenSSLLoaded();\r
 void SetSSLTimeoutCallback(DWORD Timeout, LPSSLTIMEOUTCALLBACK pCallback);\r
 void SetSSLConfirmCallback(LPSSLCONFIRMCALLBACK pCallback);\r
+BOOL SetSSLRootCertificate(void* pData, DWORD Length);\r
 BOOL IsHostNameMatched(LPCSTR HostName, LPCSTR CommonName);\r
 BOOL AttachSSL(SOCKET s, SOCKET parent, BOOL* pbAborted);\r
 BOOL DetachSSL(SOCKET s);\r