Page 14 of 14

Re: Windows Filtering Platform

Posted: Tue Oct 08, 2013 9:46 pm
by JHPJHP
Thanks! You don't want to know the amount of time I spent trying to decipher the ZLib documentation... :shock:
Here is something I removed from the code I posted, it was invaluable to working through this:

Code: Select all

If *msg : Debug PeekS(*msg) : EndIf
I kept receiving the -3 error message you experienced with your script, but with this simple line the resulting message (and Google) helped me continue to the next step... and will definitely be helpful with future use of the library.

-----------------------

I like the addition - it makes sense - updated my previous post. :)

Re: Windows Filtering Platform

Posted: Tue Oct 08, 2013 10:07 pm
by Thunder93
Good stuff. JHP!

Re: Windows Filtering Platform

Posted: Wed Oct 09, 2013 12:59 am
by JHPJHP
Updated:
- new Functions: inflateGetHeader / deflateInit2_, deflateBound, deflateSetHeader, deflate, deflateEnd
- new Structure: GZ_HEADER
- InflatePayload -- inflateGetHeader -- depends on windowBits + ???
- DeflatePayload -- deflateSetHeader -- depends on windowBits + ???
- windowBits
-- 8..15 = zlib format
-- 24..31 = gzip format
-- -8..-15 = raw zlib format with no header
- tested: InflatePayload - DeflatePayload - InflatePayload (passed)

Code: Select all

#DIVERT_LAYER_NETWORK = 0
#DIVERT_PRIORITY_DEFAULT = 0
#DIVERT_FLAG_SNIFF = 1
#MAXBUF = $FFFF
#ZLIB_VERSION = "1.2.8"
#ENABLE_GZIP = 16
#ENABLE_ZLIB_GZIP = 32
#Z_FINISH = 4
#Z_DEFAULT_COMPRESSION = -1
#Z_DEFLATED = 8
#MAX_MEM_LEVEL = 9
#Z_DEFAULT_STRATEGY = 0
#Z_NULL = 0

Structure DIVERT_ADDRESS
  IfIdx.l
  SubIfIdx.l
  Direction.a
EndStructure

Structure DIVERT_IPHDR
  StructureUnion
    HdrLength.a
    Version.a
  EndStructureUnion
  TOS.a
  Length.u
  Id.u
  FragOff0.u
  TTL.a
  Protocol.a
  Checksum.u
  SrcAddr.l
  DstAddr.l
EndStructure

Structure DIVERT_TCPHDR
  SrcPort.u
  DstPort.u
  SeqNum.l
  AckNum.l
  StructureUnion
    Reserved1.a
    HdrLength.a
  EndStructureUnion
  StructureUnion
    Fin.a
    Syn.a
    Rst.a
    Psh.a
    Ack.a
    Urg.a
    Reserved2.a
  EndStructureUnion
  Window.u
  Checksum.u
  UrgPtr.u
EndStructure

Structure PAYLOAD
  HdrLengthIP.a
  HdrLengthTCP.a
  Length.u
  Id.u
  AckNum.l
  *ppData
  pDataLen.l
EndStructure

Structure Z_STREAM Align #PB_Structure_AlignC
  *next_in.Byte
  avail_in.l
  total_in.l
  *next_out.Byte
  avail_out.l
  total_out.l
  *msg.Byte
  *state
  zalloc.l
  zfree.l
  opaque.l
  data_type.i
  adler.l
  reserved.l
  CompilerIf #PB_Compiler_Processor = #PB_Processor_x64
    alignment.l
  CompilerEndIf
EndStructure

Structure GZ_HEADER Align #PB_Structure_AlignC
  text.i
  time.l
  xflags.i
  os.i
  *extra.Byte
  extra_len.l
  extra_max.l
  *name.Byte
  name_max.l
  *comment.Byte
  comm_max.l
  hcrc.i
  done.i
EndStructure

Prototype protoDivertOpen(filter.s, layer, priority.u, flags.q)
Global DivertOpen.protoDivertOpen

Prototype.b protoDivertRecv(handle, *pPacket, packetLen, pAddr, recvLen)
Global DivertRecv.protoDivertRecv

Prototype.b protoDivertHelperParsePacket(*pPacket, packetLen, *ppIpHdr, *ppIpv6Hdr, *ppIcmpHdr, *ppIcmpv6Hdr, *ppTcpHdr, *ppUdpHdr, *ppData, pDataLen)
Global DivertHelperParsePacket.protoDivertHelperParsePacket

Prototype.b protoDivertClose(handle)
Global DivertClose.protoDivertClose

Global Dim pPL.PAYLOAD(0)

ImportC "zlib.lib"
  inflateInit2_(*strm, windowBits.i, Version.s, strm_size)
  inflateGetHeader(*strm, *head)
  inflate(*strm, flush.i)
  inflateEnd(*strm)
  deflateInit2_(*strm, level.i, method.i, windowBits.i, memlevel.i, strategy.i, Version.s, strm_size)
  deflateBound(*strm, sourceLen)
  deflateSetHeader(*strm, *head)
  deflate(*strm, flush.i)
  deflateEnd(*strm)
EndImport

Procedure.s InflatePayload(*Payload, windowBits.i, GetHeader.b = #False)
  LengthToRead = MemorySize(*Payload)
  LengthToWrite = LengthToRead * 8
  *Output = AllocateMemory(LengthToWrite)
  strm.Z_STREAM
  strm\next_in = *Payload
  strm\avail_in = LengthToRead
  strm\next_out = *Output
  strm\avail_out = LengthToWrite
  strm\zalloc = #Z_NULL
  strm\zfree = #Z_NULL
  strm\opaque = #Z_NULL
  inflateInit2_(@strm, windowBits, #ZLIB_VERSION, SizeOf(Z_STREAM))

  If GetHeader
    head.GZ_HEADER
    inflateGetHeader(@strm, @head)
  EndIf
  inflate(@strm, #Z_FINISH)
  inflateEnd(@strm)
  sOutput.s = PeekS(*Output, -1, #PB_UTF8)
  FreeMemory(*Output)
  ProcedureReturn sOutput
EndProcedure

Procedure DeflatePayload(sInput.s, windowBits.i, AddHeader.b = #False)
  LengthToRead = StringByteLength(sInput)
  strm.Z_STREAM
  strm\next_in = @sInput
  strm\avail_in = LengthToRead
  strm\zalloc = #Z_NULL
  strm\zfree = #Z_NULL
  strm\opaque = #Z_NULL
  deflateInit2_(@strm, #Z_DEFAULT_COMPRESSION, #Z_DEFLATED, windowBits, #MAX_MEM_LEVEL, #Z_DEFAULT_STRATEGY, #ZLIB_VERSION, SizeOf(Z_STREAM))
  LengthToWrite = deflateBound(@strm, LengthToRead)
  *Payload = AllocateMemory(LengthToWrite)
  strm\next_out = *Payload
  strm\avail_out = LengthToWrite

  If AddHeader
    head.GZ_HEADER
    head\text = #True
    head\time = 0
    head\os = 0
    head\extra = #Z_NULL
    head\name = #Z_NULL
    head\comment = #Z_NULL
    head\hcrc = #False
    deflateSetHeader(@strm, @head)
  EndIf
  deflate(@strm, #Z_FINISH)
  deflateEnd(@strm)
  ProcedureReturn *Payload
EndProcedure

Procedure BuildPayload()
  SortStructuredArray(pPL(), #PB_Sort_Ascending, OffsetOf(PAYLOAD\Id), TypeOf(PAYLOAD\Id))

  For pCount = 0 To ArraySize(pPL()) - 1
    PacketData.s = PeekS(pPL(pCount)\ppData, pPL(pCount)\pDataLen, #PB_UTF8)

    If FindString(PacketData, "Content-Type: text/html") > 0 Or pRange
      If pPL(pCount)\pDataLen <> pPL(pCount)\Length - (pPL(pCount)\HdrLengthIP + pPL(pCount)\HdrLengthTCP)
        Debug "ERROR: Data Packet length does not match calculated Structure values"
        End
      EndIf

      If pRange
        If pPL(pCount)\AckNum <> pPL(pCount - 1)\AckNum : Break : EndIf

        pId = pPL(pCount)\Id
        plSize = MemorySize(*Payload)
        *Payload = ReAllocateMemory(*Payload, plSize + pPL(pCount)\pDataLen)
        CopyMemory(pPL(pCount)\ppData, *Payload + plSize, pPL(pCount)\pDataLen)
      Else
        pRange = #True
        pId = pPL(pCount)\Id
        plSize = 0
        pOffset = Len(Mid(PacketData, 0, FindString(PacketData, #CRLF$ + #CRLF$))) + 3
        *Payload = AllocateMemory(pPL(pCount)\pDataLen - pOffset)
        CopyMemory(pPL(pCount)\ppData + pOffset, *Payload + plSize, pPL(pCount)\pDataLen - pOffset)
      EndIf
    EndIf
  Next
  sOutput.s = InflatePayload(*Payload, 15 | #ENABLE_GZIP)
  FreeMemory(*Payload)
  *Payload = AllocateMemory(Len(sOutput))
  *Payload = DeflatePayload(sOutput, 15)
  Debug InflatePayload(*Payload, 15)
  FreeMemory(*Payload)
EndProcedure

WinDivert = OpenLibrary(#PB_Any, "WinDivert.dll")

If IsLibrary(WinDivert)
  DivertOpen = GetFunction(WinDivert, "DivertOpen")
  DivertSetParam = GetFunction(WinDivert, "DivertSetParam")
  DivertRecv = GetFunction(WinDivert, "DivertRecv")
  DivertHelperParsePacket = GetFunction(WinDivert, "DivertHelperParsePacket")
  DivertClose = GetFunction(WinDivert, "DivertClose")
  filter.s = "inbound && ip.SrcAddr == 88.191.144.148 && tcp.Ack"
  hWndDivert = DivertOpen(filter, #DIVERT_LAYER_NETWORK, #DIVERT_PRIORITY_DEFAULT, #DIVERT_FLAG_SNIFF)

  If hWndDivert <> #INVALID_HANDLE_VALUE
    pAddr.DIVERT_ADDRESS
    *ppIpHdr.DIVERT_IPHDR
    *ppTcpHdr.DIVERT_TCPHDR
    RunProgram("iexplore", "http://www.purebasic.com/", "")

    Repeat
      *pPacket = AllocateMemory(#MAXBUF)

      If DivertRecv(hWndDivert, *pPacket, #MAXBUF, @pAddr, @recvLen)
        DivertHelperParsePacket(*pPacket, recvLen, @*ppIpHdr, #Null, #Null, #Null, @*ppTcpHdr, #Null, @*ppData, @pDataLen)

        If *ppIpHdr And *ppTcpHdr
          If *ppData
            ReDim pPL(pCount)
            pPL(pCount)\HdrLengthIP = PeekA(@*ppIpHdr\Version) & %1111 * 32 / 8
            pPL(pCount)\HdrLengthTCP = PeekA(@*ppTcpHdr\HdrLength) >> 4 & %1111 * 4
            pPL(pCount)\Length = ntohs_(PeekU(@*ppIpHdr\Length))
            pPL(pCount)\Id = ntohs_(PeekU(@*ppIpHdr\Id))
            pPL(pCount)\AckNum = ntohl_(PeekL(@*ppTcpHdr\AckNum))
            pPL(pCount)\ppData = AllocateMemory(pDataLen)
            CopyMemory(*ppData, pPL(pCount)\ppData, pDataLen)
            pPL(pCount)\pDataLen = pDataLen
            pCount + 1
          EndIf

          If pCount = 1 : Debug "Please wait.... expecting TCP Fin Packet" : EndIf

          If PeekA(@*ppTcpHdr\Fin) & %1
            FreeMemory(*pPacket)
            Break
          EndIf
        EndIf
      EndIf
      FreeMemory(*pPacket)
    ForEver
    DivertClose(hWndDivert)
  EndIf
  CloseLibrary(WinDivert)
  RunProgram("sc", "stop WinDivert1.0", "", #PB_Program_Hide)
  RunProgram("sc", "delete WinDivert1.0", "", #PB_Program_Hide)
  BuildPayload()
EndIf

Re: Windows Filtering Platform

Posted: Thu Oct 10, 2013 12:50 am
by Thunder93
You have been a busy bee! Its shaping up nicely. Superb job. :D

Re: Windows Filtering Platform

Posted: Thu Oct 10, 2013 5:26 am
by JHPJHP
Thank you for saying so... Here is a link to an RFC document with a lot of great information: http://tools.ietf.org/html/rfc1952

Cheers!

Re: Windows Filtering Platform

Posted: Thu Oct 10, 2013 5:31 am
by Thunder93
Received. Thank you. :P

Re: Windows Filtering Platform

Posted: Fri Oct 18, 2013 9:48 am
by JHPJHP
Not sure if you read my last few post before I removed them... no worries - I've resolved the issue I had modifying a packets HTML script.

Cheers - its been fun!

Re: Windows Filtering Platform

Posted: Sat Oct 19, 2013 10:30 pm
by Thunder93
Apologies. I've been swamped with work, and still working and no time to relax and play programming. It has been fun, and I'm not looking to end this. :twisted:

Re: Windows Filtering Platform

Posted: Mon Oct 21, 2013 8:29 pm
by JHPJHP
Not looking to end this eh, then I guess I'll share my last two weeks of sleepless nights. As with all our scripts, this is not an "across the board" solution, but a good start to some of the requirements needed. If I'm sounding vague it's because I want the script to speak for itself. Please run Replace2 first, and fill in the password field - no it doesn't have to be your correct password, :) then press the Connect button.

There is more to say about the script - things to be aware of, but I will get into greater detail later.

Re: Windows Filtering Platform

Posted: Mon Oct 21, 2013 8:38 pm
by Thunder93
Received. :)

Re: Windows Filtering Platform

Posted: Tue Oct 22, 2013 3:17 am
by JHPJHP
Hi Thunder93,

Things to be aware of:

The three files utilize the same script, but the PureBasic site reacts differently then the WinDivert site. Which is why it took me so long to figure out how to get a proper working example.

There is a magic number that was the key to making it work: 2920 : 2 x 1460

I got the first script somewhat working with the PureBasic site, but when I ran it on the WinDivert site, the page was messed up. But having two reference points I started to make comparisons...

If the first (*header) packet grabbed is greater then 2920 then that amount will be missing from the first (*header) packet. It must then be adjusted in the next (*replace) accumlated packet, which is what happens when loading the PureBasic site.

If the first (*header) packet grabbed is less then 2920, then the first (*header) packet needs to be padded with the difference, which is what happens when loading the WinDivert site.
- see the top line of "View Source" after running the Replace3 script - it contains an empty string (padding)

If your modifying the html script from the first (*header) packet grabbed, and the size is less then whats being replace - it will need to be padded, if its larger then no problem.

Code: Select all

replacedata = ReplaceString(replacedata, "bypassing", RSet("JHPJHP", Len("bypassing")))
When modifying html script - it needs to be after the last call to pLength = StringByteLength(replacedata) - in both the first (*header) and next (*replace) packet grabs.

- deviation from any of the above rules will usually corrupt a page, which can be seen from "View Source"
-- like what was observed during the tests you performed on the first working block script

Not all sites use gzip, or will respond to the method I have here, but I believe that is just a matter of simple changes.

Re: Windows Filtering Platform

Posted: Tue Oct 22, 2013 3:38 am
by Thunder93
I saw that twisted evil face! Apologies for leaving you hanging! :wink:

I didn't have chance, I've been AFK. I'm back now and I began putting something together. Which may clarify up some key points. Hopefully I don't run into any math situations :lol:

Re: Windows Filtering Platform

Posted: Tue Oct 22, 2013 4:05 am
by JHPJHP
I look forward to your key points when you're ready.

Cheers!

Re: Windows Filtering Platform

Posted: Wed Oct 23, 2013 12:03 am
by Thunder93
Hey JHP! Bud! You misunderstood me. At that time I hadn't had the chance to do more than simply skim through your code. I was so in and out of reality lastnight that when I said about key points that I meant some possible solutions to our existing problems. Hopefully also looking to expand on the various HTTP delivery methods.

I had the chance to try out and have close look at your codes and I must say... I'm pretty impressed with what you accomplished here. You are really making distance, superb work JHP.

.. Though it is a good thing your not here, I likely would of bumped you in the head for that previous post of yours. :lol: