2014-12-01 23:55:08 +01:00
|
|
|
|
// swad_cryptography.c: cryptography
|
|
|
|
|
|
|
|
|
|
/*
|
|
|
|
|
SWAD (Shared Workspace At a Distance),
|
|
|
|
|
is a web platform developed at the University of Granada (Spain),
|
|
|
|
|
and used to support university teaching.
|
|
|
|
|
|
|
|
|
|
This file is part of SWAD core.
|
2021-02-09 12:43:45 +01:00
|
|
|
|
Copyright (C) 1999-2021 Antonio Ca<EFBFBD>as Vargas
|
2014-12-01 23:55:08 +01:00
|
|
|
|
|
|
|
|
|
This program is free software: you can redistribute it and/or modify
|
|
|
|
|
it under the terms of the GNU Affero 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 Affero General Public License for more details.
|
|
|
|
|
|
|
|
|
|
You should have received a copy of the GNU Affero General Public License
|
|
|
|
|
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
|
|
|
*/
|
|
|
|
|
/*****************************************************************************/
|
|
|
|
|
/********************************* Headers ***********************************/
|
|
|
|
|
/*****************************************************************************/
|
|
|
|
|
|
|
|
|
|
#include <string.h> // For string functions
|
|
|
|
|
#include <unistd.h> // For access, lstat, getpid, chdir, symlink
|
|
|
|
|
|
|
|
|
|
#include "sha2/sha2.h" // For sha-256 and sha-512 algorithms
|
2016-04-04 14:48:12 +02:00
|
|
|
|
#include "swad_constant.h"
|
2014-12-01 23:55:08 +01:00
|
|
|
|
#include "swad_cryptography.h"
|
2016-04-04 14:48:12 +02:00
|
|
|
|
#include "swad_global.h"
|
|
|
|
|
|
|
|
|
|
/*****************************************************************************/
|
|
|
|
|
/****************************** Public constants *****************************/
|
|
|
|
|
/*****************************************************************************/
|
|
|
|
|
|
|
|
|
|
/*****************************************************************************/
|
2019-11-21 16:47:07 +01:00
|
|
|
|
/***************************** Private constants *****************************/
|
2016-04-04 14:48:12 +02:00
|
|
|
|
/*****************************************************************************/
|
|
|
|
|
|
|
|
|
|
/*****************************************************************************/
|
2019-11-21 16:47:07 +01:00
|
|
|
|
/******************************* Private types *******************************/
|
2016-04-04 14:48:12 +02:00
|
|
|
|
/*****************************************************************************/
|
2014-12-01 23:55:08 +01:00
|
|
|
|
|
|
|
|
|
/*****************************************************************************/
|
|
|
|
|
/************** External global variables from others modules ****************/
|
|
|
|
|
/*****************************************************************************/
|
|
|
|
|
|
2016-04-04 14:48:12 +02:00
|
|
|
|
extern struct Globals Gbl;
|
2019-03-15 15:25:31 +01:00
|
|
|
|
extern const char Str_BIN_TO_BASE64URL[64 + 1];
|
2014-12-01 23:55:08 +01:00
|
|
|
|
|
|
|
|
|
/*****************************************************************************/
|
2019-11-21 16:47:07 +01:00
|
|
|
|
/************************* Private global variables **************************/
|
2014-12-01 23:55:08 +01:00
|
|
|
|
/*****************************************************************************/
|
|
|
|
|
|
|
|
|
|
/***** SHA-256 algorithm *****/
|
|
|
|
|
|
|
|
|
|
#define BITS_SHA256_ENCRYPTION 256
|
|
|
|
|
#define BYTES_SHA256_ENCRYPTION (BITS_SHA256_ENCRYPTION/8)
|
|
|
|
|
|
|
|
|
|
/***** SHA-512 algorithm *****/
|
|
|
|
|
|
|
|
|
|
#define BITS_SHA512_ENCRYPTION 512
|
|
|
|
|
#define BYTES_SHA512_ENCRYPTION (BITS_SHA512_ENCRYPTION/8)
|
|
|
|
|
|
|
|
|
|
/*****************************************************************************/
|
2019-11-21 16:47:07 +01:00
|
|
|
|
/***************************** Private prototypes ****************************/
|
2014-12-01 23:55:08 +01:00
|
|
|
|
/*****************************************************************************/
|
|
|
|
|
|
|
|
|
|
/*****************************************************************************/
|
|
|
|
|
/*************** Encrypt a plain text using SHA=256 algorithm ****************/
|
|
|
|
|
/*****************************************************************************/
|
|
|
|
|
|
|
|
|
|
// Pointers to PlainText and EncryptedText can point to the same place
|
2017-01-28 15:58:46 +01:00
|
|
|
|
void Cry_EncryptSHA256Base64 (const char *PlainText,
|
2017-03-07 01:56:41 +01:00
|
|
|
|
char EncryptedText[Cry_BYTES_ENCRYPTED_STR_SHA256_BASE64 + 1])
|
2014-12-01 23:55:08 +01:00
|
|
|
|
{
|
|
|
|
|
int i,j;
|
|
|
|
|
unsigned char digest256[SHA256_DIGEST_SIZE];
|
|
|
|
|
|
|
|
|
|
/* Encrypt function */
|
|
|
|
|
sha256 ((const unsigned char *) PlainText, strlen (PlainText), digest256);
|
|
|
|
|
|
|
|
|
|
/* Copy digest256 into EncryptedText, changing from binary to BASE64 */
|
|
|
|
|
for (i = 0, j = 0;
|
|
|
|
|
i < BYTES_SHA256_ENCRYPTION;
|
|
|
|
|
i += 3) // 256 bits, 32 bytes
|
|
|
|
|
{
|
2017-01-28 15:58:46 +01:00
|
|
|
|
EncryptedText[j++] = Str_BIN_TO_BASE64URL [ (digest256[ i ] & 0xFC) >> 2];
|
2014-12-01 23:55:08 +01:00
|
|
|
|
if (i == (BYTES_SHA256_ENCRYPTION-2)) // i == 30, j == 42, last character to fill in encrypted text
|
|
|
|
|
{
|
2017-01-28 15:58:46 +01:00
|
|
|
|
EncryptedText[j++] = Str_BIN_TO_BASE64URL [((digest256[ i ] & 0x03) << 4) | ((digest256[i + 1] & 0xF0) >> 4)];
|
|
|
|
|
EncryptedText[ j ] = Str_BIN_TO_BASE64URL [((digest256[i + 1] & 0x0F) << 2) ];
|
2014-12-01 23:55:08 +01:00
|
|
|
|
}
|
|
|
|
|
else
|
|
|
|
|
{
|
2017-01-28 15:58:46 +01:00
|
|
|
|
EncryptedText[j++] = Str_BIN_TO_BASE64URL [((digest256[ i ] & 0x03) << 4) | ((digest256[i + 1] & 0xF0) >> 4)];
|
|
|
|
|
EncryptedText[j++] = Str_BIN_TO_BASE64URL [((digest256[i + 1] & 0x0F) << 2) | ((digest256[i + 2] & 0xC0) >> 6)];
|
|
|
|
|
EncryptedText[j++] = Str_BIN_TO_BASE64URL [ (digest256[i + 2] & 0x3F) ];
|
2014-12-01 23:55:08 +01:00
|
|
|
|
}
|
|
|
|
|
}
|
2017-03-07 01:56:41 +01:00
|
|
|
|
EncryptedText[Cry_BYTES_ENCRYPTED_STR_SHA256_BASE64] = '\0';
|
2014-12-01 23:55:08 +01:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/*****************************************************************************/
|
|
|
|
|
/*************** Encrypt a plain text using SHA=512 algorithm ****************/
|
|
|
|
|
/*****************************************************************************/
|
|
|
|
|
|
|
|
|
|
// Pointers to PlainText and EncryptedText can point to the same place
|
2017-01-28 15:58:46 +01:00
|
|
|
|
void Cry_EncryptSHA512Base64 (const char *PlainText,
|
|
|
|
|
char EncryptedText[Cry_LENGTH_ENCRYPTED_STR_SHA512_BASE64 + 1])
|
2014-12-01 23:55:08 +01:00
|
|
|
|
{
|
2017-01-28 15:58:46 +01:00
|
|
|
|
int i;
|
|
|
|
|
int j;
|
2014-12-01 23:55:08 +01:00
|
|
|
|
unsigned char digest512[SHA512_DIGEST_SIZE];
|
|
|
|
|
|
|
|
|
|
/* Encrypt function */
|
|
|
|
|
sha512 ((const unsigned char *) PlainText, strlen (PlainText), digest512);
|
|
|
|
|
|
|
|
|
|
/* Copy digest512 into EncryptedText, changing from binary to BASE64 */
|
|
|
|
|
for (i = 0, j = 0;
|
|
|
|
|
i < BYTES_SHA512_ENCRYPTION;
|
|
|
|
|
i += 3) // 512 bits, 64 bytes
|
|
|
|
|
{
|
2017-01-28 15:58:46 +01:00
|
|
|
|
EncryptedText[j++] = Str_BIN_TO_BASE64URL [ (digest512[ i ] & 0xFC) >> 2];
|
2014-12-01 23:55:08 +01:00
|
|
|
|
if (i == (BYTES_SHA512_ENCRYPTION-1)) // i == 63, j == 85, last character to fill in encrypted text
|
2017-01-28 15:58:46 +01:00
|
|
|
|
EncryptedText[ j ] = Str_BIN_TO_BASE64URL [ (digest512[ i ] & 0x03) << 4];
|
2014-12-01 23:55:08 +01:00
|
|
|
|
else
|
|
|
|
|
{
|
2017-01-28 15:58:46 +01:00
|
|
|
|
EncryptedText[j++] = Str_BIN_TO_BASE64URL [((digest512[ i ] & 0x03) << 4) | ((digest512[i + 1] & 0xF0) >> 4)];
|
|
|
|
|
EncryptedText[j++] = Str_BIN_TO_BASE64URL [((digest512[i + 1] & 0x0F) << 2) | ((digest512[i + 2] & 0xC0) >> 6)];
|
|
|
|
|
EncryptedText[j++] = Str_BIN_TO_BASE64URL [ (digest512[i + 2] & 0x3F) ];
|
2014-12-01 23:55:08 +01:00
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
EncryptedText[Cry_LENGTH_ENCRYPTED_STR_SHA512_BASE64] = '\0';
|
|
|
|
|
}
|
2016-04-04 14:48:12 +02:00
|
|
|
|
|
|
|
|
|
/*****************************************************************************/
|
|
|
|
|
/*** Create a unique name encrypted, different each time function is called **/
|
|
|
|
|
/*****************************************************************************/
|
|
|
|
|
|
2017-03-07 01:56:41 +01:00
|
|
|
|
void Cry_CreateUniqueNameEncrypted (char UniqueNameEncrypted[Cry_BYTES_ENCRYPTED_STR_SHA256_BASE64 + 1])
|
2016-04-04 14:48:12 +02:00
|
|
|
|
{
|
|
|
|
|
static unsigned NumCall = 0; // When this function is called several times in the same execution of the program, each time a new name is created
|
2019-11-08 01:10:32 +01:00
|
|
|
|
char UniqueNamePlain[Cns_MAX_BYTES_IP + Cns_MAX_DECIMAL_DIGITS_LONG + Cns_MAX_DECIMAL_DIGITS_LONG + Cns_MAX_DECIMAL_DIGITS_UINT + 1];
|
2016-04-04 14:48:12 +02:00
|
|
|
|
|
|
|
|
|
NumCall++;
|
2021-02-15 16:25:55 +01:00
|
|
|
|
snprintf (UniqueNamePlain,sizeof (UniqueNamePlain),"%s-%lx-%x-%x",
|
2018-10-17 10:32:18 +02:00
|
|
|
|
Gbl.IP,Gbl.StartExecutionTimeUTC,Gbl.PID,NumCall);
|
2016-04-04 14:48:12 +02:00
|
|
|
|
Cry_EncryptSHA256Base64 (UniqueNamePlain,UniqueNameEncrypted); // Make difficult to guess a unique name
|
|
|
|
|
}
|