|
-
Nov 5th, 2013, 04:10 PM
#1
Format Byte Array
I have found this extension useful when debugging methods that use byte arrays. It was originally written to help debug TCP/IP packets and SerialPort data. This extension formats arrays of bytes, shorts, integers, and longs in binary, and optionally shows hex, decimal, and characters. The format is shown below.
NOTE: Requires ASCIITable
Code:
Module FormatBytes
'Imports System.Runtime.CompilerServices
''' <summary>
''' Takes an array and formats it for easier reading. Shows binary by default.
''' </summary>
''' <param name="buf">the array</param>
''' <param name="showChar">show characters</param>
''' <param name="showDec">show decimal</param>
''' <param name="showHex">show hex</param>
''' <param name="dumpfile">a path string or an open IO.Stream</param>
''' <param name="encode">encoding - designed for 7-8 bit character sets</param>
''' <returns>formatted string</returns>
''' <remarks></remarks>
<Extension()>
Public Function PrettyByteBuf(buf() As Byte, _
Optional showChar As Boolean = False, _
Optional showDec As Boolean = False, _
Optional showHex As Boolean = False, _
Optional dumpfile As Object = Nothing, _
Optional encode As System.Text.Encoding = Nothing) As String
If IsNothing(buf) Then Return ""
Dim rv As New System.Text.StringBuilder
'rquires http://www.vbforums.com/showthread.php?741563-ASCII-Table
Dim atab As ASCIITable
If encode Is Nothing Then
atab = New ASCIITable
Else
atab = New ASCIITable(encode)
End If
Dim hdrl As String = "<<--------------0---------1---------2---------3----<>---4---------5---------6---------7--->>"
Dim dash As String = "---------------------------------------------------<>---------------------------------------"
Dim part As Boolean = False
Const hdrshow As Integer = 32
For idx As Integer = 0 To buf.Length - 1 Step 8
If idx Mod hdrshow = 0 Then
rv.AppendLine(hdrl)
End If
'newline
rv.Append(String.Format("{0,-10}> ", idx))
For x As Integer = 0 To 7
Dim y As Integer = x + idx
If y >= buf.Length Then
part = True
Exit For
End If
Dim ac As ASCIITable.aChar = atab.theChars(buf(y))
rv.Append(String.Format("{0,-10}", ac.bin))
Next
If showHex Then
rv.AppendLine()
rv.Append(String.Format("{0,12} ", "hex"))
For x As Integer = 0 To 7
Dim y As Integer = x + idx
If y >= buf.Length Then Exit For
Dim ac As ASCIITable.aChar = atab.theChars(buf(y))
rv.Append(String.Format("{0,-10}", ac.hex))
Next
End If
If showDec Then
rv.AppendLine()
rv.Append(String.Format("{0,12} ", "dec"))
For x As Integer = 0 To 7
Dim y As Integer = x + idx
If y >= buf.Length Then Exit For
Dim ac As ASCIITable.aChar = atab.theChars(buf(y))
rv.Append(String.Format("{0,-10}", ac.code))
Next
End If
If showChar Then
rv.AppendLine()
rv.Append(String.Format("{0,12} ", "ch"))
For x As Integer = 0 To 7
Dim y As Integer = x + idx
If y >= buf.Length Then Exit For
Dim ac As ASCIITable.aChar = atab.theChars(buf(y))
rv.Append(String.Format("{0,-10}", ac.ch))
Next
End If
If part Then rv.AppendLine()
If (showChar OrElse showDec OrElse showHex) AndAlso ((idx + 8) Mod hdrshow <> 0) Then
If Not part Then rv.AppendLine()
rv.AppendLine(dash)
Else
If Not part Then rv.AppendLine()
End If
Next
If TypeOf (dumpfile) Is String Then
Dim p As String = DirectCast(dumpfile, String)
If p <> "" Then
rv.AppendLine()
rv.AppendLine()
Try
Dim txtwr As New IO.FileStream(p, FileMode.Append, FileAccess.Write, FileShare.None)
Dim b() As Byte = atab.encodingUsed.GetBytes(rv.ToString)
txtwr.Write(b, 0, b.Length)
txtwr.Close()
txtwr.Dispose()
Catch ex As Exception
Throw
End Try
End If
ElseIf TypeOf (dumpfile) Is IO.Stream Then
Try
Dim txtwr As IO.Stream = DirectCast(dumpfile, IO.Stream)
Dim b() As Byte = atab.encodingUsed.GetBytes(rv.ToString)
txtwr.Write(b, 0, b.Length)
Catch ex As Exception
Throw
End Try
End If
Return rv.ToString
End Function
''' <summary>
''' Takes an array and formats it for easier reading. Shows binary by default.
''' </summary>
''' <param name="buf">the array</param>
''' <param name="showChar">show characters</param>
''' <param name="showDec">show decimal</param>
''' <param name="showHex">show hex</param>
''' <param name="dumpfile">a path string or an open IO.Stream</param>
''' <param name="encode">encoding - designed for 7-8 bit character sets</param>
''' <returns>formatted string</returns>
''' <remarks></remarks>
<Extension()>
Public Function PrettyByteBuf(buf() As Short, _
Optional showChar As Boolean = False, _
Optional showDec As Boolean = False, _
Optional showHex As Boolean = False, _
Optional dumpfile As Object = Nothing, _
Optional encode As System.Text.Encoding = Nothing) As String
Dim rv As New List(Of Byte)
Dim mask As Byte = &HFF
For Each n As Short In buf
For x As Integer = (16 - 8) To 0 Step -8
rv.Add(CByte((n >> x) And mask))
Next
Next
Return rv.ToArray.PrettyByteBuf(showChar, showDec, showHex, dumpfile, encode)
End Function
''' <summary>
''' Takes an array and formats it for easier reading. Shows binary by default.
''' </summary>
''' <param name="buf">the array</param>
''' <param name="showChar">show characters</param>
''' <param name="showDec">show decimal</param>
''' <param name="showHex">show hex</param>
''' <param name="dumpfile">a path string or an open IO.Stream</param>
''' <param name="encode">encoding - designed for 7-8 bit character sets</param>
''' <returns>formatted string</returns>
''' <remarks></remarks>
<Extension()>
Public Function PrettyByteBuf(buf() As Integer, _
Optional showChar As Boolean = False, _
Optional showDec As Boolean = False, _
Optional showHex As Boolean = False, _
Optional dumpfile As Object = Nothing, _
Optional encode As System.Text.Encoding = Nothing) As String
Dim rv As New List(Of Byte)
Dim mask As Byte = &HFF
For Each n As Integer In buf
For x As Integer = (32 - 8) To 0 Step -8
rv.Add(CByte((n >> x) And mask))
Next
Next
Return rv.ToArray.PrettyByteBuf(showChar, showDec, showHex, dumpfile, encode)
End Function
''' <summary>
''' Takes an array and formats it for easier reading. Shows binary by default.
''' </summary>
''' <param name="buf">the array</param>
''' <param name="showChar">show characters</param>
''' <param name="showDec">show decimal</param>
''' <param name="showHex">show hex</param>
''' <param name="dumpfile">a path string or an open IO.Stream</param>
''' <param name="encode">encoding - designed for 7-8 bit character sets</param>
''' <returns>formatted string</returns>
''' <remarks></remarks>
<Extension()>
Public Function PrettyByteBuf(buf() As Long, _
Optional showChar As Boolean = False, _
Optional showDec As Boolean = False, _
Optional showHex As Boolean = False, _
Optional dumpfile As Object = Nothing, _
Optional encode As System.Text.Encoding = Nothing) As String
Dim rv As New List(Of Byte)
Dim mask As Byte = &HFF
For Each n As Long In buf
For x As Integer = (64 - 8) To 0 Step -8
rv.Add(CByte((n >> x) And mask))
Next
Next
Return rv.ToArray.PrettyByteBuf(showChar, showDec, showHex, dumpfile, encode)
End Function
''' <summary>
''' Takes an array and formats it for easier reading. Shows binary by default.
''' </summary>
''' <param name="s">a string</param>
''' <param name="showChar">show characters</param>
''' <param name="showDec">show decimal</param>
''' <param name="showHex">show hex</param>
''' <param name="dumpfile">a path string or an open IO.Stream</param>
''' <param name="encode">encoding - designed for 7-8 bit character sets</param>
''' <returns>formatted string</returns>
''' <remarks></remarks>
<Extension()>
Public Function PrettyByteBuf(s As String, _
Optional showChar As Boolean = False, _
Optional showDec As Boolean = False, _
Optional showHex As Boolean = False, _
Optional dumpfile As Object = Nothing, _
Optional encode As System.Text.Encoding = Nothing) As String
Dim rv As New List(Of Byte)
Dim enc As System.Text.Encoding
If encode Is Nothing Then
enc = System.Text.Encoding.Default
Else
enc = encode
End If
rv.AddRange(enc.GetBytes(s))
Return rv.ToArray.PrettyByteBuf(showChar, showDec, showHex, dumpfile, encode)
End Function
End Module
Sample output - note that this looks best when formatted to display with a fixed width font
Code:
<<--------------0---------1---------2---------3----<>---4---------5---------6---------7--->>
0 > 00011110 00011111 00100000 00100001 00100010 00100011 00100100 00100101
8 > 00100110 00100111 00101000 00101001 00101010 00101011 00101100 00101101
16 > 00101110 00101111 00110000 00110001 00110010 00110011 00110100 00110101
24 > 00110110 00110111 00111000 00111001 00111010 00111011 00111100 00111101
<<--------------0---------1---------2---------3----<>---4---------5---------6---------7--->>
32 > 00111110 00111111 01000000 01000001 01000010 01000011 01000100 01000101
40 > 01000110 01000111 01001000 01001001 01001010 01001011 01001100 01001101
48 > 01001110 01001111 01010000 01010001 01010010 01010011 01010100 01010101
56 > 01010110 01010111 01011000 01011001 01011010
Code:
<<--------------0---------1---------2---------3----<>---4---------5---------6---------7--->>
0 > 00011110 00011111 00100000 00100001 00100010 00100011 00100100 00100101
hex 1E 1F 20 21 22 23 24 25
dec 30 31 32 33 34 35 36 37
ch *RS *US *SPC ! " # $ %
---------------------------------------------------<>---------------------------------------
8 > 00100110 00100111 00101000 00101001 00101010 00101011 00101100 00101101
hex 26 27 28 29 2A 2B 2C 2D
dec 38 39 40 41 42 43 44 45
ch & ' ( ) * + , -
---------------------------------------------------<>---------------------------------------
16 > 00101110 00101111 00110000 00110001 00110010 00110011 00110100 00110101
hex 2E 2F 30 31 32 33 34 35
dec 46 47 48 49 50 51 52 53
ch . / 0 1 2 3 4 5
---------------------------------------------------<>---------------------------------------
24 > 00110110 00110111 00111000 00111001 00111010 00111011 00111100 00111101
hex 36 37 38 39 3A 3B 3C 3D
dec 54 55 56 57 58 59 60 61
ch 6 7 8 9 : ; < =
<<--------------0---------1---------2---------3----<>---4---------5---------6---------7--->>
32 > 00111110 00111111 01000000 01000001 01000010 01000011 01000100 01000101
hex 3E 3F 40 41 42 43 44 45
dec 62 63 64 65 66 67 68 69
ch > ? @ A B C D E
---------------------------------------------------<>---------------------------------------
40 > 01000110 01000111 01001000 01001001 01001010 01001011 01001100 01001101
hex 46 47 48 49 4A 4B 4C 4D
dec 70 71 72 73 74 75 76 77
ch F G H I J K L M
Last edited by dbasnett; May 25th, 2015 at 11:04 AM.
-
Nov 5th, 2013, 05:15 PM
#2
Re: Format Byte Array
Here is a VS2012 Console project ready to run.
Last edited by kareninstructor; Nov 6th, 2013 at 11:38 AM.
Reason: Changed project link to updated version
-
Nov 6th, 2013, 10:15 AM
#3
Re: Format Byte Array
The code was modified in place to fix a few formatting errors and added the ability to dump the result to a file, which required a change to ASCIITable (make sure you have the latest version).
If the extension is passed a path string for the dump file it opens the file, appends the formatted string, and closes the file.
If the extension is passed an IO.Stream for the dump file it appends the formatted string. The IO.Stream must be open.
Also added support to dump strings.
Code:
Dim theChars As String = "Test ABCDEFGHIJKLMNOPQRSTUVWXYZ"
'
RichTextBox1.Text = (theChars & vbCrLf).PrettyByteBuf(True)
results in
Code:
<<--------------0---------1---------2---------3----<>---4---------5---------6---------7--->>
0 > 01010100 01100101 01110011 01110100 00100000 01000001 01000010 01000011
ch T e s t *SPC A B C
---------------------------------------------------<>---------------------------------------
8 > 01000100 01000101 01000110 01000111 01001000 01001001 01001010 01001011
ch D E F G H I J K
---------------------------------------------------<>---------------------------------------
16 > 01001100 01001101 01001110 01001111 01010000 01010001 01010010 01010011
ch L M N O P Q R S
---------------------------------------------------<>---------------------------------------
24 > 01010100 01010101 01010110 01010111 01011000 01011001 01011010 00001101
ch T U V W X Y Z *CR
<<--------------0---------1---------2---------3----<>---4---------5---------6---------7--->>
32 > 00001010
ch *LF
---------------------------------------------------<>---------------------------------------
Last edited by dbasnett; Nov 7th, 2013 at 10:17 AM.
Tags for this Thread
Posting Permissions
- You may not post new threads
- You may not post replies
- You may not post attachments
- You may not edit your posts
-
Forum Rules
|
Click Here to Expand Forum to Full Width
|