仕方がない编码器已经移植到Go语言,并进行了若干改进 | shellcode生成工具
作者:Sec-Labs | 发布时间:
项目地址
https://github.com/EgeBalci/sgn
SGN
相关技术点
- 二进制编码
- LFSR
- keystone引擎
- 代码混淆
项目用途
SGN是一种多态二进制编码器,用于生成静态不可检测的二进制有效负载,主要用于攻击性安全目的。它使用加性反馈循环对给定的二进制指令进行编码,类似于LFSR。该项目是对原始Shikata ga nai使用golang重新实现的,有很多改进。SGN通过以下改进来实现更好的编码效果:
- 64位支持。
- 新的更小的解码器存根。
- 带伪随机模式的编码存根。
- 没有可见的循环条件。
- 编码器解码存根的混淆。
- 安全寄存器选项。
SGN的主要目的是创建一个更好的编码器,将给定的二进制编码到与完全随机数据相同的程度,不可能检测到解码器的存在。SGN使用keystone引擎,是一种汇编器库,用于生成编码的汇编指令。使用SGN可以生成各种有效载荷,如shellcode、恶意软件等。

SGN是一个用于攻击性安全目的的多态二进制编码器,例如生成静态难以检测的二进制有效载荷。 它使用加性反馈循环来编码给定的二进制指令,类似于LFSR。该项目是golang中原始Shikata ga nai的重新实现,其中包含许多改进。
如何运作和为什么要使用它?
对于攻击性安全社区而言,Shikata ga nai编码器的原始实现被认为是最好的shellcode编码器(直到现在)。但是,多年来,安全研究人员发现了几个检测编码器的静态陷阱(相关工作FireEye article)。 这个项目的主要动机是创建一个更好的编码器,将给定的二进制编码到与完全随机数据相同的程度,不能检测到解码器的存在。借助于keystone汇编器库,实施以下改进。
- 64位支持。
最终正常编码的x64 shellcodes! - 新的更小的解码器存根。
LFSR密钥缩小为1字节 - 伪随机模式的编码存根。
解码器存根也使用伪随机模式编码 - 没有可见的循环条件。
存根解码自身时不使用任何循环条件!! - 解码器存根混淆。
添加了带有keystone的随机垃圾指令生成器 - 安全寄存器选项。
不使用任何寄存器(可选前奏,可能会减少多态性)
安装
可以在此处获取预编译的二进制文件。要从源代码构建,请按照以下步骤操作。
依赖性:
构建源代码的唯一依赖是keystone引擎,请按照这些说明安装该库。安装了libkeystone后,只需获取它即可。
go install github.com/EgeBalci/sgn@latest
DOCKER安装
docker pull egee/sgn
docker run -it egee/sgn
用法
-h是相当自我说明的,如果要查看幕后发生的情况,请使用-v ( ͡° ͜ʖ ͡°)_/¯

__ _ __ __ _
___ / / (_) /_____ _/ /____ _ ___ ____ _ ___ ___ _(_)
(_-</ _ \/ / '_/ _ `/ __/ _ `/ / _ `/ _ `/ / _ \/ _ `/ /
/___/_//_/_/_/\_\\_,_/\__/\_,_/ \_, /\_,_/ /_//_/\_,_/_/
========[Author:-Ege-Balcı-]====/___/=======v2.0.0=========
┻━┻ ︵ヽ(`Д´)ノ︵ ┻━┻ (ノ ゜Д゜)ノ ︵ 仕方がない
Usage: sgn [OPTIONS] <FILE>
-a int
Binary architecture (32/64) (default 32)
-asci
Generates a full ASCI printable payload (takes very long time to bruteforce)
-badchars string
Don't use specified bad characters given in hex format (\x00\x01\x02...)
-c int
Number of times to encode the binary (increases overall size) (default 1)
-h Print help
-max int
Maximum number of bytes for obfuscation (default 20)
-o string
Encoded output binary name
-plain-decoder
Do not encode the decoder stub
-safe
Do not modify and register values
-v More verbose output
Docker用法
docker run -it -v /tmp/:/tmp/ sgn /tmp/shellcode
作为库使用
警告!!SGN包仍在开发中,以实现更好的性能和多项改进。大多数函数都可能会更改。
```
package main
import (
"encoding/hex"
"fmt"
"io/ioutil"
sgn "github.com/egebalci/sgn/lib"
)
func main() {
// 首先打开一些文件
file, err := ioutil.ReadFile("myfile.bin")
if err != nil { // 检查错误
fmt.Println(err)
return
}
// 创建一个新的SGN编码器
encoder := sgn.NewEncoder()
// 设置正确的体系结构
encoder.SetArchitecture(64)
// 编码二进制文件
encodedBinary, err := encoder.Encode(file)
if err != nil {
fmt.Println(err)
return
}
// 打印编码二进制的十六进制转储
fmt.Println(hex.Dump(encodedBinary))
}
```
执行流程
下图是编码器的基本工作流程图。但请记住,每次迭代垃圾指令、解码器和模式解码器的大小、位置和顺序都会改变。

LFSR本身在概率空间方面非常强大。为了实现更多的多态性,在未编码的原始有效负载的开头附加了垃圾指令。下面的图像显示了LFSR的特征多项式的伴随矩阵,并用列向量表示种子,在k步之后以斐波那契配置的寄存器状态。
挑战
考虑到此编码器的概率空间,我个人认为任何基于规则的静态检测机制都无法检测到使用SGN编码的二进制文件。实际上,如果有人能编写一个可以检测到每个编码输出的YARA规则,我将把这个项目的捐款作为象征性奖励赠送给他们。请查看这里以获取有关索赔捐款的指南和规则。
如果您尝试并失败,请考虑捐赠 [̲̅$̲̅(̲̅ ͡° ͜ʖ ͡°̲̅)̲̅$̲̅]
