/***************************************************************************
* sslscan - A SSL cipher scanning tool *
* Copyright 2007-2009 by Ian Ventura-Whiting (Fizz) *
* fizz@titania.co.uk *
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 3 of the License, or *
* (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program. If not, see <http://www.gnu.org/licenses/>. *
* *
* In addition, as a special exception, the copyright holders give *
* permission to link the code of portions of this program with the *
* OpenSSL library under certain conditions as described in each *
* individual source file, and distribute linked combinations *
* including the two. *
* You must obey the GNU General Public License in all respects *
* for all of the code used other than OpenSSL. If you modify *
* file(s) with this exception, you may extend this exception to your *
* version of the file(s), but you are not obligated to do so. If you *
* do not wish to do so, delete this exception statement from your *
* version. If you delete this exception statement from all source *
* files in the program, then also delete it here. *
***************************************************************************/
// Includes...
#include <string.h>
#include <netdb.h>
#include <unistd.h>
#include <sys/stat.h>
#include <sys/socket.h>
#include <openssl/err.h>
#include <openssl/ssl.h>
#include <openssl/pkcs12.h>
#include <openssl/x509.h>
#include <openssl/x509v3.h>
// Defines...
#define false 0
#define true 1
#define mode_help 0
#define mode_version 1
#define mode_single 2
#define mode_multiple 3
#define BUFFERSIZE 1024
#define ssl_all 0
#define ssl_v2 1
#define ssl_v3 2
#define tls_v1 3
// Colour Console Output...
#if !defined(__WIN32__)
const char *RESET = "[0m"; // DEFAULT
const char *COL_RED = "[31m"; // RED
const char *COL_BLUE = "[34m"; // BLUE
const char *COL_GREEN = "[32m"; // GREEN
#else
const char *RESET = "";
const char *COL_RED = "";
const char *COL_BLUE = "";
const char *COL_GREEN = "";
#endif
const char *program_banner = " _\n"
" ___ ___| |___ ___ __ _ _ __\n"
" / __/ __| / __|/ __/ _` | '_ \\\n"
" \\__ \\__ \\ \\__ \\ (_| (_| | | | |\n"
" |___/___/_|___/\\___\\__,_|_| |_|\n\n"
" Version 1.8.2\n"
" http://www.titania.co.uk\n"
" Copyright Ian Ventura-Whiting 2009\n";
const char *program_version = "sslscan version 1.8.2\nhttp://www.titania.co.uk\nCopyright (C) Ian Ventura-Whiting 2009\n";
const char *xml_version = "1.8.2";
struct sslCipher
{
// Cipher Properties...
const char *name;
char *version;
int bits;
char description[512];
SSL_METHOD *sslMethod;
struct sslCipher *next;
};
struct sslCheckOptions
{
// Program Options...
char host[512];
int port;
int noFailed;
int starttls;
int sslVersion;
int targets;
int pout;
int sslbugs;
int http;
// File Handles...
FILE *xmlOutput;
// TCP Connection Variables...
struct hostent *hostStruct;
struct sockaddr_in serverAddress;
// SSL Variables...
SSL_CTX *ctx;
struct sslCipher *ciphers;
char *clientCertsFile;
char *privateKeyFile;
char *privateKeyPassword;
};
// Adds Ciphers to the Cipher List structure
int populateCipherList(struct sslCheckOptions *options, SSL_METHOD *sslMethod)
{
// Variables...
int returnCode = true;
struct sslCipher *sslCipherPointer;
int tempInt;
int loop;
STACK_OF(SSL_CIPHER) *cipherList;
SSL *ssl = NULL;
// Setup Context Object...
options->ctx = SSL_CTX_new(sslMethod);
if (options->ctx != NULL)
{
SSL_CTX_set_cipher_list(options->ctx, "ALL:COMPLEMENTOFALL");
// Create new SSL object
ssl = SSL_new(options->ctx);
if (ssl != NULL)
{
// Get List of Ciphers
cipherList = SSL_get_ciphers(ssl);
// Create Cipher Struct Entries...
for (loop = 0; loop < sk_SSL_CIPHER_num(cipherList); loop++)
{
// Create Structure...
if (options->ciphers == 0)
{
options->ciphers = malloc(sizeof(struct sslCipher));
sslCipherPointer = options->ciphers;
}
else
{
sslCipherPointer = options->ciphers;
while (sslCipherPointer->next != 0)
sslCipherPointer = sslCipherPointer->next;
sslCipherPointer->next = malloc(sizeof(struct sslCipher));
sslCipherPointer = sslCipherPointer->next;
}
// Init
memset(sslCipherPointer, 0, sizeof(struct sslCipher));
// Add cipher information...
sslCipherPointer->sslMethod = sslMethod;
sslCipherPointer->name = SSL_CIPHER_get_name(sk_SSL_CIPHER_value(cipherList, loop));
sslCipherPointer->version = SSL_CIPHER_get_version(sk_SSL_CIPHER_value(cipherList, loop));
SSL_CIPHER_description(sk_SSL_CIPHER_value(cipherList, loop), sslCipherPointer->description, sizeof(sslCipherPointer->description) - 1);
sslCipherPointer->bits = SSL_CIPHER_get_bits(sk_SSL_CIPHER_value(cipherList, loop), &tempInt);
}
// Free SSL object
SSL_free(ssl);
}
else
{
returnCode = false;
printf("%sERROR: Could not create SSL object.%s\n", COL_RED, RESET);
}
// Free CTX Object
SSL_CTX_free(options->ctx);
}
// Error Creating Context Object
else
{
returnCode = false;
printf("%sERROR: Could not create CTX object.%s\n", COL_RED, RESET);
}
return returnCode;
}
// File Exists
int fileExists(char *fileName)
{
// Variables...
struct stat fileStats;
if (stat(fileName, &fileStats) == 0)
return true;
else
return false;
}
// Read a line from the input...
void readLine(FILE *input, char *lineFromFile, int maxSize)
{
// Variables...
int stripPointer;
// Read line from file...
fgets(lineFromFile, maxSize, input);
// Clear the end-of-line stuff...
stripPointer = strlen(lineFromFile) -1;
while ((lineFromFile[stripPointer] == '\r') || (lineFromFile[stripPointer] == '\n') || (lineFromFile[stripPointer] == ' '))
{
lineFromFile[stripPointer] = 0;
stripPointer--;
}
}
// Create a TCP socket
int tcpConnect(struct sslCheckOptions *options)
{
// Variables...
int socketDescriptor;
char buffer[BUFFERSIZE];
struct sockaddr_in localAddress;
int status;
// Create Socket
socketDescriptor = socket(AF_INET, SOCK_STREAM, 0);
if(socketDescriptor < 0)
{
printf("%s ERROR: Could not open a socket.%s\n", COL_RED, RESET);
return 0;
}
// Configure Local Port
localAddress.sin_family = AF_INET;
localAddress.sin_addr.s_addr = htonl(INADDR_ANY);
localAddress.sin_port = htons(0);
status = bind(socketDescriptor, (struct sockaddr *) &localAddress, sizeof(localAddress));
if(status < 0)
{
printf("%s ERROR: Could not bind to port.%s\n", COL_RED, RESET);
return 0;
}
评论2
最新资源