version 1.10, 2006/10/06 17:26:23
|
version 1.25, 2008/12/01 17:49:56
|
|
|
//%2006//////////////////////////////////////////////////////////////////////// |
//%LICENSE//////////////////////////////////////////////////////////////// |
// | // |
// Copyright (c) 2000, 2001, 2002 BMC Software; Hewlett-Packard Development |
// Licensed to The Open Group (TOG) under one or more contributor license |
// Company, L.P.; IBM Corp.; The Open Group; Tivoli Systems. |
// agreements. Refer to the OpenPegasusNOTICE.txt file distributed with |
// Copyright (c) 2003 BMC Software; Hewlett-Packard Development Company, L.P.; |
// this work for additional information regarding copyright ownership. |
// IBM Corp.; EMC Corporation, The Open Group. |
// Each contributor licenses this file to you under the OpenPegasus Open |
// Copyright (c) 2004 BMC Software; Hewlett-Packard Development Company, L.P.; |
// Source License; you may not use this file except in compliance with the |
// IBM Corp.; EMC Corporation; VERITAS Software Corporation; The Open Group. |
// License. |
// Copyright (c) 2005 Hewlett-Packard Development Company, L.P.; IBM Corp.; |
// |
// EMC Corporation; VERITAS Software Corporation; The Open Group. |
// Permission is hereby granted, free of charge, to any person obtaining a |
// Copyright (c) 2006 Hewlett-Packard Development Company, L.P.; IBM Corp.; |
// copy of this software and associated documentation files (the "Software"), |
// EMC Corporation; Symantec Corporation; The Open Group. |
// to deal in the Software without restriction, including without limitation |
// |
// the rights to use, copy, modify, merge, publish, distribute, sublicense, |
// Permission is hereby granted, free of charge, to any person obtaining a copy |
// and/or sell copies of the Software, and to permit persons to whom the |
// of this software and associated documentation files (the "Software"), to |
// Software is furnished to do so, subject to the following conditions: |
// deal in the Software without restriction, including without limitation the |
// |
// rights to use, copy, modify, merge, publish, distribute, sublicense, and/or |
// The above copyright notice and this permission notice shall be included |
// sell copies of the Software, and to permit persons to whom the Software is |
// in all copies or substantial portions of the Software. |
// furnished to do so, subject to the following conditions: |
// |
// |
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS |
// THE ABOVE COPYRIGHT NOTICE AND THIS PERMISSION NOTICE SHALL BE INCLUDED IN |
// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF |
// ALL COPIES OR SUBSTANTIAL PORTIONS OF THE SOFTWARE. THE SOFTWARE IS PROVIDED |
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. |
// "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT |
// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY |
// LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR |
// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, |
// PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT |
// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE |
// HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN |
// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. |
// ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION |
// |
// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. |
////////////////////////////////////////////////////////////////////////// |
// | // |
//%///////////////////////////////////////////////////////////////////////////// | //%///////////////////////////////////////////////////////////////////////////// |
|
|
#ifndef SocketzOS_inline_h | #ifndef SocketzOS_inline_h |
#define SocketzOS_inline_h | #define SocketzOS_inline_h |
| |
#include <Pegasus/Common/Logger.h> | #include <Pegasus/Common/Logger.h> |
|
#include <Pegasus/Common/AuthenticationInfo.h> |
#include <sys/ioctl.h> | #include <sys/ioctl.h> |
#include <net/rtrouteh.h> | #include <net/rtrouteh.h> |
#include <net/if.h> | #include <net/if.h> |
|
|
| |
MP_Socket::MP_Socket(SocketHandle socket) | MP_Socket::MP_Socket(SocketHandle socket) |
: _socket(socket), _isSecure(false), | : _socket(socket), _isSecure(false), |
_userAuthenticated(false) |
_userAuthenticated(false), |
|
_socketWriteTimeout(PEGASUS_DEFAULT_SOCKETWRITE_TIMEOUT_SECONDS) |
{ | { |
_username[0]=0; | _username[0]=0; |
} | } |
|
|
MP_Socket::MP_Socket( | MP_Socket::MP_Socket( |
SocketHandle socket, | SocketHandle socket, |
SSLContext * sslcontext, | SSLContext * sslcontext, |
ReadWriteSem * sslContextObjectLock) |
ReadWriteSem * sslContextObjectLock, |
|
const String& ipAddress) |
: _socket(socket), | : _socket(socket), |
_userAuthenticated(false) |
_userAuthenticated(false), |
|
_socketWriteTimeout(PEGASUS_DEFAULT_SOCKETWRITE_TIMEOUT_SECONDS) |
{ | { |
PEG_METHOD_ENTER(TRC_SSL, "MP_Socket::MP_Socket()"); | PEG_METHOD_ENTER(TRC_SSL, "MP_Socket::MP_Socket()"); |
_username[0]=0; | _username[0]=0; |
|
|
| |
int MP_Socket::ATTLS_zOS_query() | int MP_Socket::ATTLS_zOS_query() |
{ | { |
struct TTLS_IOCTL ioc; // ioctl data structure |
// ioctl data structure |
|
struct TTLS_IOCTL ioc; |
int rcIoctl; | int rcIoctl; |
int errnoIoctl; | int errnoIoctl; |
int errno2Ioctl; | int errno2Ioctl; |
| |
PEG_METHOD_ENTER(TRC_SSL, "ATTLS_zOS_query()"); | PEG_METHOD_ENTER(TRC_SSL, "ATTLS_zOS_query()"); |
| |
memset(&ioc,0,sizeof(ioc)); // clean the structure |
// clean the structure |
ioc.TTLSi_Ver = TTLS_VERSION1; // set used version of structure |
memset(&ioc,0,sizeof(ioc)); |
ioc.TTLSi_Req_Type = TTLS_QUERY_ONLY; // initialize for query only |
// set used version of structure |
ioc.TTLSi_BufferPtr = NULL; // no buffer for the certificate |
ioc.TTLSi_Ver = TTLS_VERSION1; |
ioc.TTLSi_BufferLen = 0; // will not use it |
// initialize for query only |
|
ioc.TTLSi_Req_Type = TTLS_QUERY_ONLY; |
|
// no buffer for the certificate |
|
ioc.TTLSi_BufferPtr = NULL; |
|
// will not use it |
|
ioc.TTLSi_BufferLen = 0; |
| |
rcIoctl = ioctl(_socket,SIOCTTLSCTL,(char *)&ioc); | rcIoctl = ioctl(_socket,SIOCTTLSCTL,(char *)&ioc); |
errnoIoctl = errno; | errnoIoctl = errno; |
|
|
case(EINPROGRESS): | case(EINPROGRESS): |
case(EWOULDBLOCK): | case(EWOULDBLOCK): |
{ | { |
PEG_TRACE_STRING(TRC_SSL, Tracer::LEVEL4, "---> Accept pending (EWB)."); |
PEG_TRACE((TRC_SSL, Tracer::LEVEL4, |
return 0; // accept pending |
"Accept pending: %s (error code %d, reason code 0x%08X).", |
|
strerror(errnoIoctl), |
|
errnoIoctl, |
|
errno2Ioctl)); |
|
PEG_METHOD_EXIT(); |
|
// accept pending |
|
return 0; |
} | } |
case(ECONNRESET): | case(ECONNRESET): |
{ | { |
Logger::put_l(Logger::ERROR_LOG, System::CIMSERVER, Logger::SEVERE, |
Logger::put_l( |
|
Logger::STANDARD_LOG, System::CIMSERVER, |
|
Logger::INFORMATION, |
|
MessageLoaderParms( |
"Pegasus.Common.SocketzOS_inline.CONNECTION_RESET_ERROR", | "Pegasus.Common.SocketzOS_inline.CONNECTION_RESET_ERROR", |
"ATTLS reset the connection due to handshake failure. \ |
"ATTLS reset the connection due to handshake " |
Connection closed."); |
"failure. Connection closed.")); |
|
PEG_METHOD_EXIT(); |
|
// close socket |
|
return -1; |
|
} |
|
case(ENOTCONN): |
|
{ |
|
int socket_errno; |
|
SocketLength optlen = sizeof(int); |
|
getsockopt(_socket, SOL_SOCKET, SO_ERROR, |
|
(char*)&socket_errno, &optlen); |
|
PEG_TRACE((TRC_DISCARDED_DATA, Tracer::LEVEL1, |
|
"Client not connected to ATTLS. Closing socket %d : " |
|
"%s (error code %d)", |
|
_socket,strerror(socket_errno),socket_errno)); |
PEG_METHOD_EXIT(); | PEG_METHOD_EXIT(); |
|
// close socket |
return -1; | return -1; |
} | } |
default: | default: |
{ | { |
char str_errno2[10]; | char str_errno2[10]; |
sprintf(str_errno2,"%08X",errno2Ioctl); | sprintf(str_errno2,"%08X",errno2Ioctl); |
Logger::put_l(Logger::ERROR_LOG, System::CIMSERVER, Logger::SEVERE, |
Logger::put_l( |
|
Logger::ERROR_LOG, System::CIMSERVER, Logger::SEVERE, |
|
MessageLoaderParms( |
"Pegasus.Common.SocketzOS_inline.UNEXPECTED_ERROR", | "Pegasus.Common.SocketzOS_inline.UNEXPECTED_ERROR", |
"An unexpected error occurs: $0 ( errno $1, reason code 0x$2 ). \ |
"An unexpected error occurs: $0 ( errno $1, reason code " |
Connection closed." |
"0x$2 ). Connection closed.", |
,strerror(errnoIoctl),errnoIoctl,str_errno2); |
strerror(errnoIoctl), |
|
errnoIoctl, |
|
str_errno2)); |
PEG_METHOD_EXIT(); | PEG_METHOD_EXIT(); |
|
// close socket |
return -1; | return -1; |
|
|
} | } |
} // end switch(errnoIoctl) | } // end switch(errnoIoctl) |
} // -1 ioctl() | } // -1 ioctl() |
|
|
switch(ioc.TTLSi_Stat_Policy) | switch(ioc.TTLSi_Stat_Policy) |
{ | { |
case(TTLS_POL_OFF): | case(TTLS_POL_OFF): |
|
{ |
|
Logger::put_l( |
|
Logger::ERROR_LOG, System::CIMSERVER, Logger::SEVERE, |
|
MessageLoaderParms( |
|
"Pegasus.Common.SocketzOS_inline.POLICY_OFF", |
|
"ATTLS is not active for TCP-IP stack the CIM server " |
|
"is using for HTTPS connections. " |
|
"Communication not secured. Connection closed.")); |
|
PEG_METHOD_EXIT(); |
|
// close socket |
|
return -1; |
|
} |
case(TTLS_POL_NO_POLICY): | case(TTLS_POL_NO_POLICY): |
|
{ |
|
Logger::put_l( |
|
Logger::ERROR_LOG, System::CIMSERVER, Logger::SEVERE, |
|
MessageLoaderParms( |
|
"Pegasus.Common.SocketzOS_inline.NO_POLICY", |
|
"There is no ATTLS policy found for the CIM server " |
|
"HTTPS connections. " |
|
"Communication not secured. Connection closed.")); |
|
PEG_METHOD_EXIT(); |
|
// close socket |
|
return -1; |
|
} |
case(TTLS_POL_NOT_ENABLED): | case(TTLS_POL_NOT_ENABLED): |
{ | { |
Logger::put_l(Logger::ERROR_LOG, System::CIMSERVER, Logger::SEVERE, |
Logger::put_l( |
|
Logger::ERROR_LOG, System::CIMSERVER, Logger::SEVERE, |
|
MessageLoaderParms( |
"Pegasus.Common.SocketzOS_inline.POLICY_NOT_ENABLED", | "Pegasus.Common.SocketzOS_inline.POLICY_NOT_ENABLED", |
"ATTLS policy is not aktive for the CIM Server HTTPS port. \ |
"ATTLS policy is not active for the CIM Server HTTPS port. " |
Communication not secured. Connection closed."); |
"Communication not secured. Connection closed.")); |
PEG_METHOD_EXIT(); | PEG_METHOD_EXIT(); |
|
// close socket |
return -1; | return -1; |
} | } |
case(TTLS_POL_ENABLED): | case(TTLS_POL_ENABLED): |
{ | { |
break; // a policy exists so it is ensured that a secured connectio will be established |
// a policy exists so it is ensured that a secured connection will |
|
// be established |
|
break; |
} | } |
case(TTLS_POL_APPLCNTRL): | case(TTLS_POL_APPLCNTRL): |
{ | { |
Logger::put_l(Logger::ERROR_LOG, System::CIMSERVER, Logger::SEVERE, |
Logger::put_l( |
|
Logger::ERROR_LOG, System::CIMSERVER, Logger::SEVERE, |
|
MessageLoaderParms( |
"Pegasus.Common.SocketzOS_inline.APPLCNTRL", | "Pegasus.Common.SocketzOS_inline.APPLCNTRL", |
"ATTLS policy not valid for CIM Server. \ |
"ATTLS policy not valid for CIM Server. Set " |
Set ApplicationControlled to OFF. Connection closed."); |
"ApplicationControlled to OFF. Connection closed.")); |
PEG_METHOD_EXIT(); | PEG_METHOD_EXIT(); |
|
// close socket |
return -1; | return -1; |
|
|
} | } |
| |
} // end switch(ioc.TTLSi_Stat_Policy) | } // end switch(ioc.TTLSi_Stat_Policy) |
|
|
case(TTLS_CONN_HS_INPROGRESS): | case(TTLS_CONN_HS_INPROGRESS): |
{ | { |
// the SSL handshake has not been finished yet, try late again. | // the SSL handshake has not been finished yet, try late again. |
PEG_TRACE_STRING(TRC_SSL, Tracer::LEVEL4, "---> Accept pending."); |
PEG_TRACE_CSTRING(TRC_SSL, Tracer::LEVEL4, |
|
"ATTLS reports SSL handshake pending."); |
|
// accept pending |
return 0; | return 0; |
} | } |
case(TTLS_CONN_SECURE): | case(TTLS_CONN_SECURE): |
{ | { |
break; // the connection is secure |
// the connection is secure |
|
break; |
} | } |
| |
| |
|
|
case(TTLS_SEC_UNKNOWN): | case(TTLS_SEC_UNKNOWN): |
case(TTLS_SEC_CLIENT): | case(TTLS_SEC_CLIENT): |
{ | { |
Logger::put_l(Logger::ERROR_LOG, System::CIMSERVER, Logger::SEVERE, |
Logger::put_l( |
|
Logger::ERROR_LOG, System::CIMSERVER, Logger::SEVERE, |
|
MessageLoaderParms( |
"Pegasus.Common.SocketzOS_inline.WRONG_ROLE", | "Pegasus.Common.SocketzOS_inline.WRONG_ROLE", |
"ATTLS policy specifies the wrong HandshakeRole for the CIM Server HTTPS port. \ |
"ATTLS policy specifies the wrong HandshakeRole for the " |
Communication not secured. Connection closed."); |
"CIM Server HTTPS port. Communication not secured. " |
|
"Connection closed.")); |
PEG_METHOD_EXIT(); | PEG_METHOD_EXIT(); |
|
// close connection |
return -1; | return -1; |
| |
} | } |
|
|
case(TTLS_SEC_SRV_CA_FULL): | case(TTLS_SEC_SRV_CA_FULL): |
case(TTLS_SEC_SRV_CA_REQD): | case(TTLS_SEC_SRV_CA_REQD): |
{ | { |
PEG_TRACE_STRING(TRC_SSL, Tracer::LEVEL4, |
PEG_TRACE_CSTRING(TRC_SSL, Tracer::LEVEL4, |
"---> ATTLS Securtiy Type is valid but no SAFCHK."); |
"ATTLS Security Type is valid but no SAFCHK."); |
PEG_METHOD_EXIT(); | PEG_METHOD_EXIT(); |
|
// successfull return |
return 1; | return 1; |
} | } |
| |
case(TTLS_SEC_SRV_CA_SAFCHK): | case(TTLS_SEC_SRV_CA_SAFCHK): |
{ | { |
_userAuthenticated=true; | _userAuthenticated=true; |
|
_authType=AuthenticationInfoRep::AUTH_TYPE_ZOS_ATTLS; |
memcpy(_username,ioc.TTLSi_UserID,ioc.TTLSi_UserID_Len); | memcpy(_username,ioc.TTLSi_UserID,ioc.TTLSi_UserID_Len); |
_username[ioc.TTLSi_UserID_Len]=0; // null terminated string | _username[ioc.TTLSi_UserID_Len]=0; // null terminated string |
__etoa(_username); // the user name is in EBCDIC ! |
__e2a_s(_username); // the user name is in EBCDIC! |
PEG_TRACE((TRC_SSL, Tracer::LEVEL2, | PEG_TRACE((TRC_SSL, Tracer::LEVEL2, |
"---> ATTLS Securtiy Type is SAFCHK. Resolved user ID \'%s\'",_username)); |
"ATTLS Security Type is SAFCHK. Resolved user ID \'%s\'", |
|
_username)); |
PEG_METHOD_EXIT(); | PEG_METHOD_EXIT(); |
|
// successfull return |
return 1; | return 1; |
| |
} | } |
} // end switch(ioc.TTLSi_Sec_Type) | } // end switch(ioc.TTLSi_Sec_Type) |
// This should never be reached | // This should never be reached |
PEG_TRACE_STRING(TRC_SSL, Tracer::LEVEL4, |
PEG_TRACE_CSTRING(TRC_SSL, Tracer::LEVEL1, |
"---> Never reach this! New/wrong return value of ioctl()."); |
"Received unexpected return value of ioctl(SIOCTTLSCTL)."); |
PEG_METHOD_EXIT(); | PEG_METHOD_EXIT(); |
return -1; | return -1; |
} // end ATTLS_zOS_Query | } // end ATTLS_zOS_Query |
| |
|
int MP_Socket::LocalSocket_zOS_query() |
|
{ |
|
// This function is only available in z/OS 1.8 and greater |
|
#if (__TARGET_LIB__ >= 0x41080000) |
|
|
|
struct __sect_s ioSec; |
|
int rcIoctl; |
|
int errnoIoctl; |
|
int errno2Ioctl; |
|
|
|
PEG_METHOD_ENTER(TRC_SSL, "LocalSocket_zOS_query()"); |
|
|
|
|
|
// clean the structure |
|
memset(&ioSec,0,sizeof(ioSec)); |
|
|
|
// Query the local socket for security information. |
|
rcIoctl = ioctl(_socket,SECIGET_T,(char *)&ioSec); |
|
errnoIoctl = errno; |
|
errno2Ioctl =__errno2(); |
|
|
|
// If an error occures, the error is written to the trace |
|
// but the function will successfully return. |
|
|
|
if (rcIoctl < 0) |
|
{ |
|
switch (errnoIoctl) |
|
{ |
|
case(EBADF): |
|
{ |
|
PEG_TRACE_CSTRING(TRC_SSL, Tracer::LEVEL1, |
|
"Not a valid socket descriptor for " |
|
"query local authentication."); |
|
break; |
|
} |
|
case(EINVAL): |
|
{ |
|
PEG_TRACE_CSTRING(TRC_SSL, Tracer::LEVEL1, |
|
"The local authentication request is not valid" |
|
" or not supported on this socket."); |
|
break; |
|
} |
|
case(ENODEV): |
|
{ |
|
PEG_TRACE_CSTRING(TRC_SSL, Tracer::LEVEL2, |
|
"Not a local socket descriptor."); |
|
break; |
|
} |
|
default: |
|
{ |
|
PEG_TRACE((TRC_SSL, Tracer::LEVEL1, |
|
"An unexpected error occurs: %s ( errno $d, reason code " |
|
"0x%08X ). ", |
|
strerror(errnoIoctl), |
|
errnoIoctl, |
|
errno2Ioctl)); |
|
break; |
|
} // end default |
|
} // end switch errnoIoctl |
|
|
|
PEG_METHOD_EXIT(); |
|
return 1; |
|
|
|
} // if rcIoctl < 0 |
|
|
|
// Is client task level security information available ? |
|
if (ioSec.__sectt_useridlen != 0) |
|
{ |
|
_userAuthenticated=true; |
|
_authType=AuthenticationInfoRep::AUTH_TYPE_ZOS_LOCAL_DOMIAN_SOCKET; |
|
memcpy(_username,ioSec.__sectt_userid,ioSec.__sectt_useridlen); |
|
// null terminated string |
|
_username[ioSec.__sectt_useridlen]=0; |
|
// the user name is in EBCDIC! |
|
__e2a_s(_username); |
|
PEG_TRACE((TRC_SSL, Tracer::LEVEL3, |
|
"Local Socket authentication. Resolved task level user ID \'%s\'", |
|
_username)); |
|
PEG_METHOD_EXIT(); |
|
return 1; |
|
|
|
} |
|
|
|
// Is client process level security information available ? |
|
if (ioSec.__sectp_useridlen != 0) |
|
{ |
|
_userAuthenticated=true; |
|
_authType=AuthenticationInfoRep::AUTH_TYPE_ZOS_LOCAL_DOMIAN_SOCKET; |
|
memcpy(_username,ioSec.__sectp_userid,ioSec.__sectp_useridlen); |
|
// null terminated string |
|
_username[ioSec.__sectp_useridlen]=0; |
|
// the user name is in EBCDIC! |
|
__e2a_s(_username); |
|
PEG_TRACE((TRC_SSL, Tracer::LEVEL3, |
|
"Local Socket authentication. " |
|
"Resolved process level user ID \'%s\'", |
|
_username)); |
|
PEG_METHOD_EXIT(); |
|
return 1; |
|
|
|
} |
|
|
|
// This should never be reached |
|
PEG_TRACE_CSTRING(TRC_SSL, Tracer::LEVEL1, |
|
"Received unexpected return value of ioctl(SECIGET_T)."); |
|
PEG_METHOD_EXIT(); |
|
return -1; |
|
#else |
|
return 1; |
|
#endif // (__TARGET_LIB__ >= 0x41080000) |
|
} |
|
|
| |
PEGASUS_NAMESPACE_END | PEGASUS_NAMESPACE_END |
#endif | #endif |