@@ -39,6 +39,11 @@ with this program. If not, see <https://www.gnu.org/licenses/>
39
39
#include " platform.h"
40
40
#include " util.h"
41
41
42
+ #pragma comment(lib, "crypt32.lib")
43
+ #include < Windows.h>
44
+ #include < Wincrypt.h>
45
+ #define MY_ENCODING_TYPE (PKCS_7_ASN_ENCODING | X509_ASN_ENCODING)
46
+
42
47
obs_data_t *get_module_config ()
43
48
{
44
49
const auto confPath = obs_module_config_path (" config.json" );
@@ -516,4 +521,116 @@ std::string releaseType()
516
521
c = tolower (c);
517
522
}
518
523
return rt == " release" ? " " : " " + rt;
519
- }
524
+ }
525
+
526
+ std::string binaryToString (const BYTE* binaryData, DWORD dataLen, DWORD flags = CRYPT_STRING_BASE64) {
527
+ DWORD stringLen = 0 ;
528
+ // Get the required string length, not including the null terminator.
529
+ if (!CryptBinaryToStringA (binaryData, dataLen, flags, nullptr , &stringLen)) {
530
+ obs_log (LOG_ERROR, " Could not convert binary data to string." );
531
+ return " " ;
532
+ }
533
+
534
+ // Allocate memory for the string, including the null terminator.
535
+ std::string encodedString;
536
+ encodedString.resize (stringLen);
537
+
538
+ // Perform the actual conversion.
539
+ if (!CryptBinaryToStringA (binaryData, dataLen, flags, encodedString.data (), &stringLen)) {
540
+ obs_log (LOG_ERROR, " Could not convert binary data to string." );
541
+ return " " ;
542
+ }
543
+ return encodedString;
544
+ }
545
+
546
+ DATA_BLOB stringToBinary (const std::string& input, DWORD flags = CRYPT_STRING_BASE64) {
547
+ DWORD binarySize = 0 ;
548
+ DATA_BLOB output;
549
+ output.pbData = nullptr ;
550
+ output.cbData = 0 ;
551
+ // Get the required size for the binary data
552
+ if (!CryptStringToBinaryA (input.c_str (), (DWORD)input.length (), flags, nullptr , &binarySize, nullptr , nullptr )) {
553
+ obs_log (LOG_INFO, " Could not string to binary. Could not determine needed binary data size." );
554
+ return output;
555
+ }
556
+
557
+ // Allocate memory for the binary data
558
+ output.pbData = (BYTE*)LocalAlloc (LMEM_FIXED, binarySize);
559
+ if (output.pbData == nullptr ) {
560
+ obs_log (LOG_INFO, " Could not convert string to binary. Memory allocation error." );
561
+ return output;
562
+ }
563
+ output.cbData = binarySize;
564
+ // Perform the actual conversion
565
+ if (!CryptStringToBinaryA (input.c_str (), (DWORD)input.length (), flags, output.pbData , &binarySize, nullptr , nullptr )) {
566
+ obs_log (LOG_INFO, " Could not string to binary. Invalid conversion." );
567
+ return output;
568
+ }
569
+ return output;
570
+ }
571
+
572
+ // Encrypts a string, and returns string of encrypted binary data
573
+ // as a formatted BASE 64 encoded string.
574
+ std::string encryptString (std::string input)
575
+ {
576
+ DATA_BLOB DataIn;
577
+ DATA_BLOB DataOut;
578
+ BYTE* pbDataInput = (BYTE*)input.c_str ();
579
+ DWORD cbDataInput = DWORD (strlen ((char *)pbDataInput) + 1 );
580
+ DataIn.pbData = pbDataInput;
581
+ DataIn.cbData = cbDataInput;
582
+ std::string encrypted = " " ;
583
+ if (CryptProtectData (
584
+ &DataIn,
585
+ L" " ,
586
+ NULL ,
587
+ NULL ,
588
+ NULL ,
589
+ 0 ,
590
+ &DataOut))
591
+ {
592
+ // convert binary to formatted base 64 encoded string.
593
+ encrypted = binaryToString (DataOut.pbData , DataOut.cbData );
594
+ LocalFree (DataOut.pbData );
595
+ } else {
596
+ obs_log (LOG_ERROR, " Could not encrypt string." );
597
+ }
598
+ return encrypted;
599
+ }
600
+
601
+ // Decrypts a formatted base64 encoded string. First
602
+ // converts string to binary blob, then uses windows
603
+ // cryto API to decrypt the binary blob into a usable
604
+ // string
605
+ std::string decryptString (std::string input)
606
+ {
607
+ DATA_BLOB ToDecrypt = stringToBinary (input);
608
+ if (ToDecrypt.pbData == nullptr ) {
609
+ return " " ;
610
+ }
611
+ DATA_BLOB DataVerify;
612
+ LPWSTR pDescrOut = NULL ;
613
+
614
+ std::string decrypted = " " ;
615
+
616
+ if (CryptUnprotectData (
617
+ &ToDecrypt,
618
+ &pDescrOut,
619
+ NULL ,
620
+ NULL ,
621
+ NULL ,
622
+ 0 ,
623
+ &DataVerify))
624
+ {
625
+ decrypted = std::string (reinterpret_cast <char *>(DataVerify.pbData ), DataVerify.cbData );
626
+ LocalFree (DataVerify.pbData );
627
+ LocalFree (pDescrOut);
628
+ if (ToDecrypt.pbData != nullptr ) {
629
+ LocalFree (ToDecrypt.pbData );
630
+ }
631
+ } else {
632
+ obs_log (LOG_ERROR, " Could not decrypt string." );
633
+ }
634
+ return decrypted;
635
+ }
636
+
0 commit comments