Scoket网络编程

这一小节我们介绍Powershell中的Socket编程,网络编程是所有语言中绕不开的核心点,下面我们通过对代码的分析来让大家对PS中的Socket有一个初步的了解。

Scoket-Tcp编程

开始之前我们先想想为什么要学习socket编程,那么最直观的是端口扫描,那么还有可能是反弹shell之类的应用。进行Socket编程只需要调用.Net框架即可,这里先使用TCP来示例:

这里是去打开一个TCP连接到本地的21端口,并获取21端口返回的Banner信息,其中GetOutput函数看不了可以先不看,其用来获取stream中的数据,主要看Main函数内容:

Tcp-Demo.ps1
function GetOutput 
{ 
    ## 创建一个缓冲区获取数据
    $buffer = new-object System.Byte[] 1024 
    $encoding = new-object System.Text.AsciiEncoding 

    $outputBuffer = "" 
    $findMore = $false 

    ## 从stream读取所有的数据,写到输出缓冲区
    do{ 
        start-sleep -m 1000 
        $findmore = $false 
        # 读取Timeout
        $stream.ReadTimeout = 1000 

        do{ 
            try { 
                $read = $stream.Read($buffer, 0, 1024) 
                if($read -gt 0){ 
                    $findmore = $true 
                    $outputBuffer += ($encoding.GetString($buffer, 0, $read)) 
                } 
            } catch { $findMore = $false; $read = 0 } 
        } while($read -gt 0) 
    } while($findmore) 

    $outputBuffer 
}

function Main{
    # 定义主机和端口
    $remoteHost = "127.0.0.1"
    $port = 21
    # 定义连接Host与Port
    $socket = new-object System.Net.Sockets.TcpClient($remoteHost, $port) 
    # 进行连接
    $stream = $socket.GetStream()
    # 获取Stream
    $writer = new-object System.IO.StreamWriter $stream 
    # 创建IO对象
    $SCRIPT:output += GetOutput 
    # 声明变量
    if($output){ 
        # 输出
        foreach($line in $output.Split("`n")) 
        {
            write-host $line 
        }
        $SCRIPT:output = "" 
    }
}
. Main

我们来看看输出结果:

这样就打开了21端口的连接,并且获取到了21端口的banner信息.

那么有过端口扫描编写的朋友肯定已经看到了,这种方式是直接打开连接,并不能获取到一些需要发包才能返回banner的端口信息,典型的80端口就是如此,我们需要给80端口发送特定的信息才能得到Response, 当然还有许多类似的端口,比如3389端口, 下面我们来看看我们如何使用powershell实现这项功能.

我们来看看输出:

我们下面对这项功能进行一个整合:

我们可以发包给一个端口,也可以直接连接一个端口,这里已经实现TCP,http,https三种常见协议的访问

那么至此我们已经完成了对TCP端口的打开并获取对应的信息,其中很多的关键代码释义我已经详细给出,我们主要以TCP为例,由于UDP应用场景相对于TCP较少,关于UDP的编写可自行编写。

这个脚本加以修改就是一个Powershell完成的扫描器了,端口扫描器我们放在下一节来分析,我们这里最后看一个反弹shell的ps脚本, 同样在注释中详细解释了代码块的作用。

简单的分析在注释已经提到, 其中Invoke-Expression -Command后接的代码都会被看作powershell来执行, 我们来看看正向连接的执行效果, 我们在172.16.50.196机器上执行下面的代码

连接这台机器, 结果如下:

反向类似执行即可

大家可以看到这个脚本的最开始有一大块注释,这些注释无疑是增强脚本可读性的关键,对于一个脚本的功能和用法都有清晰的讲解,那么我们来看看如何写这些注释呢。

最后我们使用Get-Help命令就能看到我们编辑的这些注释内容:

最后更新于

这有帮助吗?