Shellcode与加密流量之间的那些事儿

协讲和代码库

当我们在思虑加密协议时,第一个想到的很可能是安然传输层协议(TLS),由于它是针对Web安然的工业级标准。有的人可能还会想到SSH或IPSec等等,然则斟酌到这些协议所采纳的底层算法,它们着实都不适用于资本受限情况。而类似SHA-2和分组密码(例如Blowfish)这样加密哈希函数也并不是为类似RFID芯片这样的占用资本较少的电子设备设计的。

在2018年4月份,NIST曾为物联网行业的轻量级加密算法执行过一个标准化进程,全部历程必要好几年的光阴才可以完成,但毫无疑问的是,全部行业并不会不停等待,由于这样会导致不安然的产品裸露在互联网中。某些密码学家选择采取主动的要领,经由过程自己的努力将他们设计的协议采纳到这些低资本耗损的设备上,此中有两个范例的算法便是BLINKER和STROBE,而响应的适用于资本受限情况的代码库有LibHydrogen和MonoCypher。

分组密码

分组密码有很多种,但AES 128可能是今朝最得当对在线流量进行加密的算法了,下面给出的是我们对不合种类分组密码的测试结果:

虽然这些加密算法都异常优秀,然则他们仍必要类似计数器(CTR)和基于认证的加密模块,此中最得当消息认证码(MAC)的加密算法便是LightMAC了,由于它在实现加密的历程中应用的是相同的分组密码。

流密码

别的两种针对认证加密的热门算法(AES-GCM的调换)便是ChaCha20和Poly1305了,然则ChaCha20采纳的是200字节,而Poly1305为330字节。虽然跟HMAC-SHA2比拟,Poly1305已经压缩得异常小了,但仍旧占用资本过多。

置换函数

假如你花了很多光阴去测试各类加密算法的话,你终极会发明在构造流密码、分组密码、加密认证模型、加密哈希函数和随机数天生器时,你必要的仅仅只是一个置换函数。下面这个表格给出的是我们针对三种函数的测试结果:

这里我们选择应用Gimli,由于它占用资本起码,并且可以用来构造针对通信流量的加密算法。

异或密码

接下来,我们实现一个针对数据流的简单异或操作(Just For Fun!)。下面的截图中显示的是一台Windows虚拟机发送给Linux虚拟机的部分敕令,此中Linux平台运行的Shellcode是没有采纳任何加密的。

捕捉到两台主机间的通信数据之后,我们可以看到如下所示的TCP流数据:

给Shellcode x86汇编代码中添加部分敕令后,我们就可以进行8位异或运算了:

;

; read(r, buf, BUFSIZ, 0);

xoresi, esi; esi = 0

movecx, edi; ecx = buf

cdq; edx = 0

movdl, BUFSIZ; edx = BUFSIZ

pushSYS_read; eax = SYS_read

popeax

int0x80

; encrypt/decrypt buffer

pushad

xchgeax, ecx

xor_loop:

xorbyte[eax+ecx-1], XOR_KEY

loopxor_loop

popad

; write(w, buf, len);

xchgeax, edx; edx = len

moval, SYS_write

popebx; s or in[1]

int0x80

jmppoll_wait

经由过程在新的会话中履行相同的敕令,通信数据将无法直接可读,我这里应用了haxdump来查看发送的敕令以及接管到的结果:

当然了,长度为8位的密钥是无法有效阻拦进击者规复出通信明文的,下图给出的是Cyberchef爆破密钥的历程:

[1] [2] [3] [4] [5]下一页

Speck和LightMAC

一开始,我应用的是下面这段代码来对数据包的加密进行验证,它应用了Encrypt-then-MAC (EtM),而且这种措施比其他的措施要更安然,比如说MAC-then-Encrypt (MtE) 或Encrypt-and-MAC(E&M):

bits32

%defineSPECK_RNDS27

%defineN8

%defineK16

;奸淫奸淫奸淫奸淫奸淫奸淫奸淫奸淫奸淫奸淫奸淫奸淫奸淫**

;Light MAC parameters based on SPECK64-128

;

; N =64-bits

; K =128-bits

;

%defineCOUNTER_LENGTH N/2; should be 2

%defineBLOCK_LENGTHN; equal to N

%defineTAG_LENGTHN; >= 64-bits &&

%defineBC_KEY_LENGTHK; K

%defineENCRYPT_BLK speck_encrypt

%defineGET_MAC lightmac

%defineLIGHTMAC_KEY_LENGTH BC_KEY_LENGTH*2 ; K*2

%definek0 edi

%definek1 ebp

%definek2 ecx

%definek3 esi

%definex0 ebx

%definex1 edx

; esi= IN data

; ebp= IN key

speck_encrypt:

pushad

pushesi; save M

lodsd; x0 = x->w[0]

xchgeax, x0

lodsd; x1 = x->w[1]

xchgeax, x1

movesi, ebp; esi = key

lodsd

xchgeax, k0; k0 = key[0]

lodsd

xchgeax, k1; k1 = key[1]

lodsd

xchgeax, k2; k2 = key[2]

lodsd

xchgeax, k3; k3 = key[3]

xoreax, eax; i = 0

spk_el:

; x0 = (ROTR32(x0, 8) + x1) ^ k0;

rorx0, 8

addx0, x1

xorx0, k0

; x1 = ROTL32(x1, 3) ^ x0;

rolx1, 3

xorx1, x0

; k1 = (ROTR32(k1, 8) + k0) ^ i;

rork1, 8

addk1, k0

xork1, eax

; k0 = ROTL32(k0, 3) ^ k1;

rolk0, 3

xork0, k1

xchgk3, k2

xchgk3, k1

; i++

inceax

cmpal, SPECK_RNDS

jnzspk_el

popedi

xchgeax, x0; x->w[0] = x0

stosd

xchgeax, x1; x->w[1] = x1

stosd

popad

ret

; edx= IN len

; ebx= IN msg

; ebp= IN key

; edi= OUT tag

lightmac:

pushad

movecx, edx

xoredx, edx

addebp, BLOCK_LENGTH + BC_KEY_LENGTH

上一页[1] [2] [3] [4] [5]下一页

pushad; allocate N-bytes for M

; zero initialize T

mov[edi+0], edx; t->w[0] = 0;

mov[edi+4], edx; t->w[1] = 0;

; while we have msg data

lmx_l0:

movesi, esp; esi = M

jecxzlmx_l2; exit loop ifmsglen == 0

lmx_l1:

; add byte to M

moval, [ebx]; al = *data++

incebx

mov[esi+edx+COUNTER_LENGTH], al

incedx; idx++

; M filled?

cmpdl, BLOCK_LENGTH – COUNTER_LENGTH

; –msglen

loopne lmx_l1

jnelmx_l2

; add S counter in big endian format

incdword[esp+_edx]; ctr++

moveax, [esp+_edx]

; reset index

cdq; idx = 0

bswapeax; m.ctr =SWAP32(ctr)

mov[esi], eax

; encrypt M with E using K1

callENCRYPT_BLK

; update T

lodsd; t->w[0] ^= m.w[0];

xor[edi+0], eax

lodsd; t->w[1] ^= m.w[1];

xor[edi+4], eax

jmplmx_l0; keep going

lmx_l2:

; add the end bit

movbyte[esi+edx+COUNTER_LENGTH], 0x80

xchgesi, edi; swap T and M

lmx_l3:

; update T with any msg dataremaining

moval, [edi+edx+COUNTER_LENGTH]

xor[esi+edx], al

decedx

jnslmx_l3

; advance key to K2

addebp, BC_KEY_LENGTH

; encrypt T with E using K2

callENCRYPT_BLK

popad; release memory for M

popad; restore registers

ret

; IN:ebp = global memory, edi = msg, ecx = enc flag, edx = msglen

;OUT: -1 or length of data encrypted/decrypted

encrypt:

push-1

popeax; set return valueto -1

pushad

leaebp, [ebp+@ctx] ; ebp crypto ctx

movebx, edi; ebx = msg

pushad; allocate 8-bytes fortag+strm

上一页[1] [2] [3] [4] [5]下一页

movedi, esp; edi = tag

; if (enc) {

;verify tag + decrypt

jecxzenc_l0

; msglen -= TAG_LENGTH;

subedx, TAG_LENGTH

jleenc_l5; return -1 if msglen 0

mov[esp+_edx], edx

; GET_MAC(ctx, msg, msglen, mac);

callGET_MAC

; memcmp(mac, &msg[msglen],TAG_LENGTH)

leaesi, [ebx+edx] ; esi = &msg[msglen]

cmpsd

jnzenc_l5; not equal? return-1

cmpsd

jnzenc_l5; ditto

; MACs are equal

; zero the MAC

xoreax, eax

mov[esi-4], eax

mov[esi-8], eax

enc_l0:

movedi, esp

testedx, edx; exit if (msglen== 0)

jzenc_lx

; memcpy (strm, ctx->e_ctr,BLOCK_LENGTH);

movesi, [esp+_ebp]; esi = ctx->e_ctr

pushedi

movsd

movsd

movebp, esi

popesi

; ENCRYPT_BLK(ctx->e_key, &strm);

callENCRYPT_BLK

movcl, BLOCK_LENGTH

; r=(len > BLOCK_LENGTH) ?BLOCK_LENGTH : len;

enc_l2:

lodsb; al = *strm++

xor[ebx], al; *msg ^= al

incebx; msg++

decedx

loopnz enc_l2; while (!ZF&& –ecx)

movcl, BLOCK_LENGTH

enc_l3:; do {

; update counter

movebp, [esp+_ebp]

incbyte[ebp+ecx-1]

loopzenc_l3; } while (ZF&& –ecx)

jmpenc_l0

enc_lx:

; encrypting? add MAC of ciphertext

decdword[esp+_ecx]

movedx, [esp+_edx]

jzenc_l4

movedi, ebx

movebx, [esp+_ebx]

movebp, [esp+_ebp]

; GET_MAC(ctx, buf, buflen, msg);

callGET_MAC

; msglen += TAG_LENGTH;

addedx, TAG_LENGTH

enc_l4:

; return msglen;

mov[esp+32+_eax], edx

enc_l5:

popad

popad

ret

必要留意的是,这里还得用到一个协议,接管方在对数据有效性进行验证之前必要知道发送方到底发送了若干数据过来,是以加密长度必要首先发送,接下来才是加密数据。然则请等一下,这里明明应该是Shellcode,为什么现在搞得那么繁杂呢?试一下RC4?不,请大年夜家往下看!

上一页[1] [2] [3] [4] [5]下一页

Gimli

为了应用Gimli来代替RC4,我编写了下面这段代码,这里的置换函数本色上便是Gimli:

#defineR(v,n)(((v)>>(n))|((v)

#defineF(n)for(i=0;i

#defineX(a,b)(t)=(s[a]),(s[a])=(s[b]),(s[b])=(t)

voidpermute(void*p){

uint32_t i,r,t,x,y,z,*s=p;

for(r=24;r>0;–r){

F(4)

x=R(s[i],24),

y=R(s[4+i],9),

z=s[8+i],

s[8+i]=x^(z+z)^((y&z)*4),

s[4+i]=y^x^((x|z)*2),

s[i]=z^y^((x&y)*8);

t=r&3;

if(!t)

X(0,1),X(2,3),

*s^=0x9e377900|r;

if(t==2)X(0,2),X(1,3);

}

}

typedefstruct _crypt_ctx {

uint32_t idx;

intfdr, fdw;

uint8_t s[48];

uint8_t buf[BUFSIZ];

}crypt_ctx;

uint8_tgf_mul(uint8_t x) {

return (x > 7) *0x1b);

}

//initialize crypto context

voidinit_crypt(crypt_ctx *c, int r, int w, void *key) {

int i;

c->fdr = r; c->fdw = w;

for(i=0;i

c->s[i] = ((uint8_t*)key)[i % 16] ^gf_mul(i);

}

permute(c->s);

c->idx = 0;

}

//encrypt or decrypt buffer

voidcrypt(crypt_ctx *c) {

int i, len;

// read from socket or stdout

len = read(c->fdr, c->buf, BUFSIZ);

// encrypt/decrypt

for(i=0;i

if(c->idx >= 32) {

permute(c->s);

c->idx = 0;

}

c->buf[i] ^= c->s[c->idx++];

}

// write to socket or stdin

write(c->fdw, c->buf, len);

}

在Linux Shell中应用这段代码之前,我们必要声明两个零丁的加密高低文来处置惩罚输入、输出和128位的静态密钥:

//using a static 128-bit key

crypt_ctx*c, c1, c2;

// echo -n top_secret_key | openssl md5-binary -out key.bin

// xxd -i key.bin

uint8_t key[] = {

0x4f, 0xef, 0x5a, 0xcc, 0x15, 0x78, 0xf6,0x01,

0xee, 0xa1, 0x4e, 0x24, 0xf1, 0xac, 0xf9,0x49 };

在进入主输出轮回之前,我们还必要对每一个高低文初始化文件读取和写入描述符,这样可以削减代码的行数:

//

// c1 is for reading from socket andwriting to stdin

init_crypt(&c1, s, in[1], key);

// c2 is for reading from stdout andwriting to socket

init_crypt(&c2, out[0], s, key);

// now loop until user exits or someother error

for (;;) {

r = epoll_wait(efd, &evts, 1,-1);

// error? bail out

if (r0) break;

// not input? bail out

if (!(evts.events & EPOLLIN))break;

fd = evts.data.fd;

c = (fd == s) ? &c1 : &c2;

crypt(c);

}

总结

对shellcode进行规复之后,将能够获得明文数据,由于我在这里加密所采纳的是一个静态密钥,为了防止这种环境呈现,大年夜家可以考试测验应用类似Diffie-Hellman这样的密钥互换协议来实现,这个就留给大年夜家自己着手考试测验啦!

上一页[1] [2] [3] [4] [5]

赞(0) 打赏
分享到: 更多 (0)
免责申明:本站所有资料均来自于网络,版权归原创者所有!本站不提供任何保证,不保证真实性,并不承担任何法律责任

评论 抢沙发

  • 昵称 (必填)
  • 邮箱 (必填)
  • 网址

阿里云优惠网 更专业 更优惠

阿里云优惠券阿里云大礼包