This is an automated email from the ASF dual-hosted git repository.

sruehl pushed a commit to branch develop
in repository https://gitbox.apache.org/repos/asf/plc4x.git

commit 6ba5bbe7f6c407ec66a296431952764f4ba658f1
Author: Sebastian Rühl <[email protected]>
AuthorDate: Sat Apr 17 15:56:18 2021 +0200

    plc4go: fixed issues in length calculation in hex
    
    + calculated DefaultWidth so that it can contain 10 bytes per line in most 
cases
    + removed panic from undumpable items
    + fixed issues with sizes too small
    + moved size calculation to separate function
---
 plc4go/internal/plc4go/spi/utils/asciiBox.go      |  12 +-
 plc4go/internal/plc4go/spi/utils/asciiBox_test.go | 362 ++++++++++------
 plc4go/internal/plc4go/spi/utils/hex.go           |  93 ++--
 plc4go/internal/plc4go/spi/utils/hex_test.go      | 503 ++++++++++++++++++++--
 4 files changed, 792 insertions(+), 178 deletions(-)

diff --git a/plc4go/internal/plc4go/spi/utils/asciiBox.go 
b/plc4go/internal/plc4go/spi/utils/asciiBox.go
index 9969686..0e2cda4 100644
--- a/plc4go/internal/plc4go/spi/utils/asciiBox.go
+++ b/plc4go/internal/plc4go/spi/utils/asciiBox.go
@@ -27,8 +27,12 @@ import (
        "strings"
 )
 
+// AsciiBox is a string surrounded by a ascii border (and a optional name)
 type AsciiBox string
 
+// DebugAsciiBox set to true to get debug messages
+var DebugAsciiBox bool
+
 // Width returns the width of the box without the newlines
 func (m AsciiBox) Width() int {
        maxWidth := 0
@@ -41,7 +45,7 @@ func (m AsciiBox) Width() int {
        return maxWidth
 }
 
-// Boxer is used to render something in a box
+// AsciiBoxer is used to render something in a box
 type AsciiBoxer interface {
        // Box where int param is the proposed width
        Box(string, int) AsciiBox
@@ -96,7 +100,7 @@ func BoxAnything(name string, anything interface{}, 
charWidth int) AsciiBox {
        }
 }
 
-// BoxString boxes a box
+// BoxBox boxes a box
 func BoxBox(name string, box AsciiBox, charWidth int) AsciiBox {
        return BoxString(name, string(box), charWidth)
 }
@@ -105,7 +109,9 @@ func BoxBox(name string, box AsciiBox, charWidth int) 
AsciiBox {
 func BoxString(name string, data string, charWidth int) AsciiBox {
        longestLine := AsciiBox(data).Width()
        if charWidth < longestLine {
-               log.Debug().Msgf("Overflow by %d chars", longestLine-charWidth)
+               if DebugAsciiBox {
+                       log.Debug().Msgf("Overflow by %d chars", 
longestLine-charWidth)
+               }
                charWidth = longestLine + 2
        }
        boxedString := ""
diff --git a/plc4go/internal/plc4go/spi/utils/asciiBox_test.go 
b/plc4go/internal/plc4go/spi/utils/asciiBox_test.go
index b746ace..5b8788f 100644
--- a/plc4go/internal/plc4go/spi/utils/asciiBox_test.go
+++ b/plc4go/internal/plc4go/spi/utils/asciiBox_test.go
@@ -19,7 +19,10 @@
 
 package utils
 
-import "testing"
+import (
+       "strings"
+       "testing"
+)
 
 func TestBoxAnything(t *testing.T) {
        type args struct {
@@ -39,9 +42,11 @@ func TestBoxAnything(t *testing.T) {
                                anything:  true,
                                charWidth: 0,
                        },
-                       want: `╔═exampleBool╗
+                       want: `
+╔═exampleBool╗
 ║    true    ║
-╚════════════╝`,
+╚════════════╝
+`,
                },
                {
                        name: "test int",
@@ -50,9 +55,11 @@ func TestBoxAnything(t *testing.T) {
                                anything:  1,
                                charWidth: 0,
                        },
-                       want: `╔═exampleInt╗
+                       want: `
+╔═exampleInt╗
 ║     1     ║
-╚═══════════╝`,
+╚═══════════╝
+`,
                },
                {
                        name: "test int 123123123",
@@ -61,13 +68,16 @@ func TestBoxAnything(t *testing.T) {
                                anything:  123123123,
                                charWidth: 0,
                        },
-                       want: `╔═exampleInt╗
+                       want: `
+╔═exampleInt╗
 ║ 123123123 ║
-╚═══════════╝`,
+╚═══════════╝
+`,
                },
        }
        for _, tt := range tests {
                t.Run(tt.name, func(t *testing.T) {
+                       tt.want = trimBox(tt.want)
                        if got := BoxAnything(tt.args.name, tt.args.anything, 
tt.args.charWidth); got != tt.want {
                                t.Errorf("BoxAnything() = '\n%v\n', want 
'\n%v\n'", got, tt.want)
                        }
@@ -88,12 +98,15 @@ func TestBoxSideBySide(t *testing.T) {
                {
                        name: "Test2Boxes",
                        args: args{
-                               box1: `000 0x: 31  32  33  34  35  36  37  38  
'12345678'
+                               box1: `
+000 0x: 31  32  33  34  35  36  37  38  '12345678'
 008 0x: 39  30  61  62  63  64  65  66  '90abcdef'
 016 0x: 67  68  69  6a  6b  6c  6d  6e  'ghijklmn'
 024 0x: 6f  70  71  72  73  74  75  76  'opqrstuv'
-032 0x: 77  78  79  7a                  'wxyz    '`,
-                               box2: `╔═super nice 
data══════════════════════════════════════════════════════════════════════════════════════════════════════════════════════╗
+032 0x: 77  78  79  7a                  'wxyz    '
+`,
+                               box2: `
+╔═super nice 
data══════════════════════════════════════════════════════════════════════════════════════════════════════════════════════╗
 ║  000 0x: 31  32  33  34  35  36  37  38  39  30  61  62  63  64  65  66  67  
68  69  6a  6b  6c  6d  6e  '1234567890abcdefghijklmn'  ║
 ║  024 0x: 6f  70  71  72  73  74  75  76  77  78  79  7a  d3  31  32  33  34  
35  36  37  38  39  30  61  'opqrstuvwxyz.1234567890a'  ║
 ║  048 0x: 62  63  64  65  66  67  68  69  6a  6b  6c  6d  6e  6f  70  71  72  
73  74  75  76  77  78  79  'bcdefghijklmnopqrstuvwxy'  ║
@@ -101,9 +114,11 @@ func TestBoxSideBySide(t *testing.T) {
 ║  096 0x: 6b  6c  6d  6e  6f  70  71  72  73  74  75  76  77  78  79  7a  d3  
31  32  33  34  35  36  37  'klmnopqrstuvwxyz.1234567'  ║
 ║  120 0x: 38  39  30  61  62  63  64  65  66  67  68  69  6a  6b  6c  6d  6e  
6f  70  71  72  73  74  75  '890abcdefghijklmnopqrstu'  ║
 ║  144 0x: 76  77  78  79  7a  d3  61  61  62                                  
                            'vwxyz.aab               '  ║
-╚══════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════╝`,
+╚══════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════╝
+`,
                        },
-                       want: `000 0x: 31  32  33  34  35  36  37  38  
'12345678'╔═super nice 
data══════════════════════════════════════════════════════════════════════════════════════════════════════════════════════╗
+                       want: `
+000 0x: 31  32  33  34  35  36  37  38  '12345678'╔═super nice 
data══════════════════════════════════════════════════════════════════════════════════════════════════════════════════════╗
 008 0x: 39  30  61  62  63  64  65  66  '90abcdef'║  000 0x: 31  32  33  34  
35  36  37  38  39  30  61  62  63  64  65  66  67  68  69  6a  6b  6c  6d  6e  
'1234567890abcdefghijklmn'  ║
 016 0x: 67  68  69  6a  6b  6c  6d  6e  'ghijklmn'║  024 0x: 6f  70  71  72  
73  74  75  76  77  78  79  7a  d3  31  32  33  34  35  36  37  38  39  30  61  
'opqrstuvwxyz.1234567890a'  ║
 024 0x: 6f  70  71  72  73  74  75  76  'opqrstuv'║  048 0x: 62  63  64  65  
66  67  68  69  6a  6b  6c  6d  6e  6f  70  71  72  73  74  75  76  77  78  79  
'bcdefghijklmnopqrstuvwxy'  ║
@@ -111,58 +126,78 @@ func TestBoxSideBySide(t *testing.T) {
                                                   ║  096 0x: 6b  6c  6d  6e  
6f  70  71  72  73  74  75  76  77  78  79  7a  d3  31  32  33  34  35  36  37  
'klmnopqrstuvwxyz.1234567'  ║
                                                   ║  120 0x: 38  39  30  61  
62  63  64  65  66  67  68  69  6a  6b  6c  6d  6e  6f  70  71  72  73  74  75  
'890abcdefghijklmnopqrstu'  ║
                                                   ║  144 0x: 76  77  78  79  
7a  d3  61  61  62                                                              
'vwxyz.aab               '  ║
-                                                  
╚══════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════╝`,
+                                                  
╚══════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════╝
+`,
                },
                {
                        name: "another 2 boxes",
                        args: args{
-                               box1: `╔═exampleInt╗
+                               box1: `
+╔═exampleInt╗
 ║     4     ║
-╚═══════════╝`,
-                               box2: `╔═exampleInt╗
+╚═══════════╝
+`,
+                               box2: `
+╔═exampleInt╗
 ║     7     ║
-╚═══════════╝`,
+╚═══════════╝
+`,
                        },
-                       want: `╔═exampleInt╗╔═exampleInt╗
+                       want: `
+╔═exampleInt╗╔═exampleInt╗
 ║     4     ║║     7     ║
-╚═══════════╝╚═══════════╝`,
+╚═══════════╝╚═══════════╝
+`,
                },
                {
                        name: "size difference first box",
                        args: args{
-                               box1: `╔═exampleInt╗
+                               box1: `
+╔═exampleInt╗
 ║     4     ║
 ║     4     ║
-╚═══════════╝`,
-                               box2: `╔═exampleInt╗
+╚═══════════╝
+`,
+                               box2: `
+╔═exampleInt╗
 ║     7     ║
-╚═══════════╝`,
+╚═══════════╝
+`,
                        },
-                       want: `╔═exampleInt╗╔═exampleInt╗
+                       want: `
+╔═exampleInt╗╔═exampleInt╗
 ║     4     ║║     7     ║
 ║     4     ║╚═══════════╝
-╚═══════════╝             `,
+╚═══════════╝             
+`,
                },
                {
                        name: "size difference second box",
                        args: args{
-                               box1: `╔═exampleInt╗
+                               box1: `
+╔═exampleInt╗
 ║     4     ║
-╚═══════════╝`,
-                               box2: `╔═exampleInt╗
+╚═══════════╝
+`,
+                               box2: `
+╔═exampleInt╗
 ║     7     ║
 ║     7     ║
-╚═══════════╝`,
+╚═══════════╝
+`,
                        },
-                       want: `╔═exampleInt╗╔═exampleInt╗
+                       want: `
+╔═exampleInt╗╔═exampleInt╗
 ║     4     ║║     7     ║
 ╚═══════════╝║     7     ║
-             ╚═══════════╝`,
+             ╚═══════════╝
+`,
                },
        }
        for _, tt := range tests {
                t.Run(tt.name, func(t *testing.T) {
-                       if got := BoxSideBySide(tt.args.box1, tt.args.box2); 
got != tt.want {
+                       tt.want = trimBox(tt.want)
+                       if got := BoxSideBySide(trimBox(tt.args.box1), 
trimBox(tt.args.box2)); got != tt.want {
                                t.Errorf("BoxSideBySide() = '\n%v\n', want 
'\n%v\n'", got, tt.want)
                        }
                })
@@ -182,57 +217,69 @@ func TestBoxBelowBox(t *testing.T) {
                {
                        name: "Test2Boxes",
                        args: args{
-                               box1: `000 0x: 31  32  33  34  35  36  37  38  
'12345678'
-008 0x: 39  30  61  62  63  64  65  66  '90abcdef'
-016 0x: 67  68  69  6a  6b  6c  6d  6e  'ghijklmn'
-024 0x: 6f  70  71  72  73  74  75  76  'opqrstuv'
-032 0x: 77  78  79  7a                  'wxyz    '`,
-                               box2: `╔═super nice 
data══════════════════════════════════════════════════════════════════════════════════════════════════════════════════════╗
-║  000 0x: 31  32  33  34  35  36  37  38  39  30  61  62  63  64  65  66  67  
68  69  6a  6b  6c  6d  6e  '1234567890abcdefghijklmn'  ║
-║  024 0x: 6f  70  71  72  73  74  75  76  77  78  79  7a  d3  31  32  33  34  
35  36  37  38  39  30  61  'opqrstuvwxyz.1234567890a'  ║
-║  048 0x: 62  63  64  65  66  67  68  69  6a  6b  6c  6d  6e  6f  70  71  72  
73  74  75  76  77  78  79  'bcdefghijklmnopqrstuvwxy'  ║
-║  072 0x: 7a  d3  61  61  31  32  33  34  35  36  37  38  39  30  61  62  63  
64  65  66  67  68  69  6a  'z.aa1234567890abcdefghij'  ║
-║  096 0x: 6b  6c  6d  6e  6f  70  71  72  73  74  75  76  77  78  79  7a  d3  
31  32  33  34  35  36  37  'klmnopqrstuvwxyz.1234567'  ║
-║  120 0x: 38  39  30  61  62  63  64  65  66  67  68  69  6a  6b  6c  6d  6e  
6f  70  71  72  73  74  75  '890abcdefghijklmnopqrstu'  ║
-║  144 0x: 76  77  78  79  7a  d3  61  61  62                                  
                            'vwxyz.aab               '  ║
-╚══════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════╝`,
+                               box1: `
+000 31  32  33  34  35  36  37  38  '12345678'
+008 39  30  61  62  63  64  65  66  '90abcdef'
+016 67  68  69  6a  6b  6c  6d  6e  'ghijklmn'
+024 6f  70  71  72  73  74  75  76  'opqrstuv'
+032 77  78  79  7a                  'wxyz    '
+`,
+                               box2: `
+╔═super nice 
data══════════════════════════════════════════════════════════════════════════════════════════════════════════════════╗
+║  000 31  32  33  34  35  36  37  38  39  30  61  62  63  64  65  66  67  68  
69  6a  6b  6c  6d  6e  '1234567890abcdefghijklmn'  ║
+║  024 6f  70  71  72  73  74  75  76  77  78  79  7a  d3  31  32  33  34  35  
36  37  38  39  30  61  'opqrstuvwxyz.1234567890a'  ║
+║  048 62  63  64  65  66  67  68  69  6a  6b  6c  6d  6e  6f  70  71  72  73  
74  75  76  77  78  79  'bcdefghijklmnopqrstuvwxy'  ║
+║  072 7a  d3  61  61  31  32  33  34  35  36  37  38  39  30  61  62  63  64  
65  66  67  68  69  6a  'z.aa1234567890abcdefghij'  ║
+║  096 6b  6c  6d  6e  6f  70  71  72  73  74  75  76  77  78  79  7a  d3  31  
32  33  34  35  36  37  'klmnopqrstuvwxyz.1234567'  ║
+║  120 38  39  30  61  62  63  64  65  66  67  68  69  6a  6b  6c  6d  6e  6f  
70  71  72  73  74  75  '890abcdefghijklmnopqrstu'  ║
+║  144 76  77  78  79  7a  d3  61  61  62                                      
                        'vwxyz.aab               '  ║
+╚══════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════╝
+`,
                        },
-                       want: `000 0x: 31  32  33  34  35  36  37  38  
'12345678'                                                                      
                
-008 0x: 39  30  61  62  63  64  65  66  '90abcdef'                             
                                                         
-016 0x: 67  68  69  6a  6b  6c  6d  6e  'ghijklmn'                             
                                                         
-024 0x: 6f  70  71  72  73  74  75  76  'opqrstuv'                             
                                                         
-032 0x: 77  78  79  7a                  'wxyz    '                             
                                                         
-╔═super nice 
data══════════════════════════════════════════════════════════════════════════════════════════════════════════════════════╗
-║  000 0x: 31  32  33  34  35  36  37  38  39  30  61  62  63  64  65  66  67  
68  69  6a  6b  6c  6d  6e  '1234567890abcdefghijklmn'  ║
-║  024 0x: 6f  70  71  72  73  74  75  76  77  78  79  7a  d3  31  32  33  34  
35  36  37  38  39  30  61  'opqrstuvwxyz.1234567890a'  ║
-║  048 0x: 62  63  64  65  66  67  68  69  6a  6b  6c  6d  6e  6f  70  71  72  
73  74  75  76  77  78  79  'bcdefghijklmnopqrstuvwxy'  ║
-║  072 0x: 7a  d3  61  61  31  32  33  34  35  36  37  38  39  30  61  62  63  
64  65  66  67  68  69  6a  'z.aa1234567890abcdefghij'  ║
-║  096 0x: 6b  6c  6d  6e  6f  70  71  72  73  74  75  76  77  78  79  7a  d3  
31  32  33  34  35  36  37  'klmnopqrstuvwxyz.1234567'  ║
-║  120 0x: 38  39  30  61  62  63  64  65  66  67  68  69  6a  6b  6c  6d  6e  
6f  70  71  72  73  74  75  '890abcdefghijklmnopqrstu'  ║
-║  144 0x: 76  77  78  79  7a  d3  61  61  62                                  
                            'vwxyz.aab               '  ║
-╚══════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════╝`,
+                       want: `
+000 31  32  33  34  35  36  37  38  '12345678'                                 
                                                     
+008 39  30  61  62  63  64  65  66  '90abcdef'                                 
                                                     
+016 67  68  69  6a  6b  6c  6d  6e  'ghijklmn'                                 
                                                     
+024 6f  70  71  72  73  74  75  76  'opqrstuv'                                 
                                                     
+032 77  78  79  7a                  'wxyz    '                                 
                                                     
+╔═super nice 
data══════════════════════════════════════════════════════════════════════════════════════════════════════════════════╗
+║  000 31  32  33  34  35  36  37  38  39  30  61  62  63  64  65  66  67  68  
69  6a  6b  6c  6d  6e  '1234567890abcdefghijklmn'  ║
+║  024 6f  70  71  72  73  74  75  76  77  78  79  7a  d3  31  32  33  34  35  
36  37  38  39  30  61  'opqrstuvwxyz.1234567890a'  ║
+║  048 62  63  64  65  66  67  68  69  6a  6b  6c  6d  6e  6f  70  71  72  73  
74  75  76  77  78  79  'bcdefghijklmnopqrstuvwxy'  ║
+║  072 7a  d3  61  61  31  32  33  34  35  36  37  38  39  30  61  62  63  64  
65  66  67  68  69  6a  'z.aa1234567890abcdefghij'  ║
+║  096 6b  6c  6d  6e  6f  70  71  72  73  74  75  76  77  78  79  7a  d3  31  
32  33  34  35  36  37  'klmnopqrstuvwxyz.1234567'  ║
+║  120 38  39  30  61  62  63  64  65  66  67  68  69  6a  6b  6c  6d  6e  6f  
70  71  72  73  74  75  '890abcdefghijklmnopqrstu'  ║
+║  144 76  77  78  79  7a  d3  61  61  62                                      
                        'vwxyz.aab               '  ║
+╚══════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════╝`,
                },
                {
                        name: "different sized boxes",
                        args: args{
-                               box1: `╔═sampleField════════════╗
+                               box1: `
+╔═sampleField════════════╗
 ║123123123123123123123123║
-╚════════════════════════╝`,
-                               box2: `╔═sampleField╗
+╚════════════════════════╝
+`,
+                               box2: `
+╔═sampleField╗
 ║123123123123║
-╚════════════╝`,
+╚════════════╝
+`,
                        },
-                       want: `╔═sampleField════════════╗
+                       want: `
+╔═sampleField════════════╗
 ║123123123123123123123123║
 ╚════════════════════════╝
 ╔═sampleField╗            
 ║123123123123║            
-╚════════════╝            `,
+╚════════════╝            
+`,
                },
        }
        for _, tt := range tests {
                t.Run(tt.name, func(t *testing.T) {
-                       if got := BoxBelowBox(tt.args.box1, tt.args.box2); got 
!= tt.want {
+                       tt.want = trimBox(tt.want)
+                       if got := BoxBelowBox(trimBox(tt.args.box1), 
trimBox(tt.args.box2)); got != tt.want {
                                t.Errorf("BoxSideBySide() = '\n%v\n', want 
'\n%v\n'", got, tt.want)
                        }
                })
@@ -257,9 +304,11 @@ func TestBoxString(t *testing.T) {
                                data:      "123123123123",
                                charWidth: 1,
                        },
-                       want: `╔═sampleField╗
+                       want: `
+╔═sampleField╗
 ║123123123123║
-╚════════════╝`,
+╚════════════╝
+`,
                },
                {
                        name: "simplebox-unamed",
@@ -268,9 +317,11 @@ func TestBoxString(t *testing.T) {
                                data:      "123123123123",
                                charWidth: 1,
                        },
-                       want: `╔════════════╗
+                       want: `
+╔════════════╗
 ║123123123123║
-╚════════════╝`,
+╚════════════╝
+`,
                },
                {
                        name: "simplebox",
@@ -279,14 +330,17 @@ func TestBoxString(t *testing.T) {
                                data:      
"123123123123\n123123123123123123123123",
                                charWidth: 1,
                        },
-                       want: `╔═sampleField════════════╗
+                       want: `
+╔═sampleField════════════╗
 ║      123123123123      ║
 ║123123123123123123123123║
-╚════════════════════════╝`,
+╚════════════════════════╝
+`,
                },
        }
        for _, tt := range tests {
                t.Run(tt.name, func(t *testing.T) {
+                       tt.want = trimBox(tt.want)
                        if got := BoxString(tt.args.name, tt.args.data, 
tt.args.charWidth); got != tt.want {
                                t.Errorf("BoxString() = '\n%v\n', want 
'\n%v\n'", got, tt.want)
                        }
@@ -308,86 +362,115 @@ func TestAlignBoxes(t *testing.T) {
                        name: "enough space",
                        args: args{
                                boxes: []AsciiBox{
-                                       `╔═sampleField════════════╗
+                                       `
+╔═sampleField════════════╗
 ║      123123123123      ║
 ║123123ABABABABABAB123123║
-╚════════════════════════╝`,
-                                       `╔═sampleField════════════╗
+╚════════════════════════╝
+`,
+                                       `
+╔═sampleField════════════╗
 ║      123123123123      ║
 ║123123123123123123123123║
-╚════════════════════════╝`,
+╚════════════════════════╝
+`,
                                },
                                desiredWith: 1000,
                        },
-                       want: 
`╔═sampleField════════════╗╔═sampleField════════════╗
+                       want: `
+╔═sampleField════════════╗╔═sampleField════════════╗
 ║      123123123123      ║║      123123123123      ║
 ║123123ABABABABABAB123123║║123123123123123123123123║
-╚════════════════════════╝╚════════════════════════╝`,
+╚════════════════════════╝╚════════════════════════╝
+`,
                },
                {
                        name: "not enough space",
                        args: args{
                                boxes: []AsciiBox{
-                                       `╔═sampleField════════════╗
+                                       `
+╔═sampleField════════════╗
 ║      123123123123      ║
 ║123123ABABABABABAB123123║
-╚════════════════════════╝`,
-                                       `╔═sampleField════════════╗
+╚════════════════════════╝
+`,
+                                       `
+╔═sampleField════════════╗
 ║      123123123123      ║
 ║123123123123123123123123║
-╚════════════════════════╝`,
+╚════════════════════════╝
+`,
                                },
                                desiredWith: 0,
                        },
-                       want: `╔═sampleField════════════╗
+                       want: `
+╔═sampleField════════════╗
 ║      123123123123      ║
 ║123123ABABABABABAB123123║
 ╚════════════════════════╝
 ╔═sampleField════════════╗
 ║      123123123123      ║
 ║123123123123123123123123║
-╚════════════════════════╝`,
+╚════════════════════════╝
+`,
                },
                {
                        name: "not enough space should result in multiple rows",
                        args: args{
                                boxes: []AsciiBox{
-                                       `╔═sampleField════════════╗
+                                       `
+╔═sampleField════════════╗
 ║      123123123123      ║
 ║123123ABABABABABAB123123║
-╚════════════════════════╝`,
-                                       `╔═sampleField════════════╗
+╚════════════════════════╝
+`,
+                                       `
+╔═sampleField════════════╗
 ║      123123123123      ║
 ║123123123123123123123123║
-╚════════════════════════╝`,
-                                       `╔═sampleField════════════╗
+╚════════════════════════╝
+`,
+                                       `
+╔═sampleField════════════╗
 ║      123123123123      ║
 ║123123ABABABABABAB123123║
-╚════════════════════════╝`,
-                                       `╔═sampleField════════════╗
+╚════════════════════════╝
+`,
+                                       `
+╔═sampleField════════════╗
 ║      123123123123      ║
 ║123123123123123123123123║
-╚════════════════════════╝`,
-                                       `╔═sampleField════════════╗
+╚════════════════════════╝
+`,
+                                       `
+╔═sampleField════════════╗
 ║      123123123123      ║
 ║123123ABABABABABAB123123║
-╚════════════════════════╝`,
-                                       `╔═sampleField════════════╗
+╚════════════════════════╝
+`,
+                                       `
+╔═sampleField════════════╗
 ║      123123123123      ║
 ║123123123123123123123123║
-╚════════════════════════╝`,
-                                       `╔═sampleField════════════╗
+╚════════════════════════╝
+`,
+                                       `
+╔═sampleField════════════╗
 ║      123123123123      ║
 ║123123ABABABABABAB123123║
-╚════════════════════════╝`,
-                                       `╔═sampleField════════════╗
+╚════════════════════════╝
+`,
+                                       `
+╔═sampleField════════════╗
 ║      123123123123      ║
 ║123123123123123123123123║
-╚════════════════════════╝`,
+╚════════════════════════╝
+`,
                                },
                                desiredWith: 65,
                        },
-                       want: 
`╔═sampleField════════════╗╔═sampleField════════════╗╔═sampleField════════════╗
+                       want: `
+╔═sampleField════════════╗╔═sampleField════════════╗╔═sampleField════════════╗
 ║      123123123123      ║║      123123123123      ║║      123123123123      ║
 ║123123ABABABABABAB123123║║123123123123123123123123║║123123ABABABABABAB123123║
 ╚════════════════════════╝╚════════════════════════╝╚════════════════════════╝
@@ -398,11 +481,16 @@ func TestAlignBoxes(t *testing.T) {
 ╔═sampleField════════════╗╔═sampleField════════════╗                          
 ║      123123123123      ║║      123123123123      ║                          
 ║123123ABABABABABAB123123║║123123123123123123123123║                          
-╚════════════════════════╝╚════════════════════════╝                          
`,
+╚════════════════════════╝╚════════════════════════╝                          
+`,
                },
        }
        for _, tt := range tests {
                t.Run(tt.name, func(t *testing.T) {
+                       for i, box := range tt.args.boxes {
+                               tt.args.boxes[i] = trimBox(box)
+                       }
+                       tt.want = trimBox(tt.want)
                        if got := AlignBoxes(tt.args.boxes, 
tt.args.desiredWith); got != tt.want {
                                t.Errorf("AlignBoxes() = '\n%v\n', want 
'\n%v\n'", got, tt.want)
                        }
@@ -418,16 +506,20 @@ func TestAsciiBox_width(t *testing.T) {
        }{
                {
                        name: "same width",
-                       m: `123123123123123
+                       m: `
+123123123123123
 123123123123123
-123123123123123`,
+123123123123123
+`,
                        want: 15,
                },
                {
                        name: "different width",
-                       m: `123123123123123
+                       m: `
+123123123123123
 123123123123123123123123123123
-123123123123123`,
+123123123123123
+`,
                        want: 30,
                },
        }
@@ -453,46 +545,70 @@ func Test_mergeHorizontal(t *testing.T) {
                        name: "3 same",
                        args: args{
                                boxes: []AsciiBox{
-                                       `123123123
+                                       `
+123123123
+123123123
 123123123
-123123123`,
-                                       `abcabcabc
+`,
+                                       `
+abcabcabc
+abcabcabc
 abcabcabc
-abcabcabc`,
-                                       `zxyzxyzxy
+`,
+                                       `
 zxyzxyzxy
-zxyzxyzxy`,
+zxyzxyzxy
+zxyzxyzxy
+`,
                                },
                        },
-                       want: `123123123abcabcabczxyzxyzxy
+                       want: `
+123123123abcabcabczxyzxyzxy
+123123123abcabcabczxyzxyzxy
 123123123abcabcabczxyzxyzxy
-123123123abcabcabczxyzxyzxy`,
+`,
                },
                {
                        name: "3 different",
                        args: args{
                                boxes: []AsciiBox{
-                                       `123123123
+                                       `
 123123123
-123123123`,
-                                       `abcabcabc
+123123123
+123123123
+`,
+                                       `
+abcabcabc
 abcabcabcabcabcabcabcabcabc
-abcabcabc`,
-                                       `zxyzxyzxy
+abcabcabc
+`,
+                                       `
+zxyzxyzxy
 zxyzxyzxy
-zxyzxyzxy`,
+zxyzxyzxy
+`,
                                },
                        },
-                       want: `123123123abcabcabc                  zxyzxyzxy
+                       want: `
+123123123abcabcabc                  zxyzxyzxy
 123123123abcabcabcabcabcabcabcabcabczxyzxyzxy
-123123123abcabcabc                  zxyzxyzxy`,
+123123123abcabcabc                  zxyzxyzxy
+`,
                },
        }
        for _, tt := range tests {
                t.Run(tt.name, func(t *testing.T) {
+                       for i, box := range tt.args.boxes {
+                               tt.args.boxes[i] = trimBox(box)
+                       }
+                       tt.want = trimBox(tt.want)
                        if got := mergeHorizontal(tt.args.boxes); got != 
tt.want {
                                t.Errorf("mergeHorizontal() = '\n%v\n', want 
'\n%v\n'", got, tt.want)
                        }
                })
        }
 }
+
+func trimBox(box AsciiBox) AsciiBox {
+       return AsciiBox(strings.Trim(string(box), "\n"))
+}
diff --git a/plc4go/internal/plc4go/spi/utils/hex.go 
b/plc4go/internal/plc4go/spi/utils/hex.go
index 6b1725c..80e9a81 100644
--- a/plc4go/internal/plc4go/spi/utils/hex.go
+++ b/plc4go/internal/plc4go/spi/utils/hex.go
@@ -24,23 +24,32 @@ import (
        "encoding/gob"
        "fmt"
        "github.com/pkg/errors"
+       "github.com/rs/zerolog/log"
+       "math"
        "strings"
 )
 
 // DefaultWidth defaults to a default screen dumps size
-const DefaultWidth = 51
+const DefaultWidth = 56 // 10 bytes per line on a []byte < 999
 
 // boxLineOverheat Overheat per line when drawing boxes
 const boxLineOverheat = 1 + 1
 
-// Dump dumps a 46 char wide hex string
+// byteWidth required size of runes required to print one bytes 2 hex digits + 
2 blanks
+const byteWidth = 2 + 2
+
+// blank size of blank
+const blankWidth = 1
+
+// DebugHex set to true to get debug messages
+var DebugHex bool
+
+// BoxedDump dumps a 56+2 char wide hex string
 func BoxedDump(name string, data []byte) string {
-       // we substract the 2 lines at the side
-       dumpWidth := DefaultWidth - boxLineOverheat
-       return string(BoxString(name, DumpFixedWidth(data, dumpWidth), 
DefaultWidth))
+       return string(BoxString(name, DumpFixedWidth(data, DefaultWidth), 
DefaultWidth+boxLineOverheat))
 }
 
-// Dump dumps a 46 char wide hex string
+// Dump dumps a 56 char wide hex string
 func Dump(data []byte) string {
        return DumpFixedWidth(data, DefaultWidth)
 }
@@ -56,33 +65,25 @@ func BoxedDumpFixedWidth(name string, data []byte, 
charWidth int) string {
 func DumpAnything(anything interface{}) string {
        convertedBytes, err := toBytes(anything)
        if err != nil {
-               panic(err)
+               if DebugHex {
+                       log.Error().Err(err).Msg("Error converting to bytes")
+               }
+               return "<undumpable>"
        }
-       return DumpFixedWidth(convertedBytes, 1)
+       return Dump(convertedBytes)
 }
 
-// TODO: test with charWidht <12
 // DumpFixedWidth dumps hex as hex string. Min width of string returned is 18 
up to supplied charWidth
-func DumpFixedWidth(data []byte, charWidth int) string {
-       if charWidth <= 0 {
-               panic("charWidth needs to be greater than 0")
+func DumpFixedWidth(data []byte, desiredCharWidth int) string {
+       if data == nil || len(data) < 1 {
+               return ""
        }
        hexString := ""
-       // 3 digits index plus one blank
-       const indexWidth = 3 + 1
-       // 2 hex digits + 2 blanks
-       const byteWidth = 2 + 2
-       // strings get quoate by 2 chars
-       const stringRenderOverheat = 2
-       const minWidth = indexWidth + byteWidth + stringRenderOverheat + 1
-       if charWidth < minWidth {
-               charWidth = minWidth + 6
-       }
-       // Formulary to calculate max bytes per row...
-       maxBytesPerRow := ((charWidth - indexWidth - stringRenderOverheat) / 
(byteWidth + 1)) - 1
+       maxBytesPerRow, indexWidth := 
calculateBytesPerRowAndIndexWidth(len(data), desiredCharWidth)
 
        for byteIndex, rowIndex := 0, 0; byteIndex < len(data); byteIndex, 
rowIndex = byteIndex+maxBytesPerRow, rowIndex+1 {
-               hexString += fmt.Sprintf("%03d 0x: ", byteIndex)
+               indexString := fmt.Sprintf("%0*d ", indexWidth, byteIndex)
+               hexString += indexString
                for columnIndex := 0; columnIndex < maxBytesPerRow; 
columnIndex++ {
                        absoluteIndex := byteIndex + columnIndex
                        if absoluteIndex < len(data) {
@@ -106,6 +107,48 @@ func DumpFixedWidth(data []byte, charWidth int) string {
        return hexString[:len(hexString)-1]
 }
 
+func calculateBytesPerRowAndIndexWidth(numberOfBytes, desiredStringWidth int) 
(int, int) {
+       if DebugHex {
+               log.Debug().Msgf("Calculating max row and index for %d number 
of bytes and a desired string width of %d", numberOfBytes, desiredStringWidth)
+       }
+       indexDigits := int(math.Log10(float64(numberOfBytes))) + 1
+       requiredIndexWidth := indexDigits + blankWidth
+       if DebugHex {
+               log.Debug().Msgf("index width %d for indexDigits %d for bytes 
%d", requiredIndexWidth, indexDigits, numberOfBytes)
+       }
+       // strings get quoted by 2 chars
+       const quoteRune = 1
+       const potentialStringRenderRune = 1
+       // 0 00  '.'
+       availableSpace := requiredIndexWidth + byteWidth + quoteRune + 
potentialStringRenderRune + quoteRune
+       if DebugHex {
+               log.Debug().Msgf("calculated %d minimal width for number of 
bytes %d", availableSpace, numberOfBytes)
+       }
+       if desiredStringWidth >= availableSpace {
+               availableSpace = desiredStringWidth
+       } else {
+               if DebugHex {
+                       log.Debug().Msgf("Overflow by %d runes", 
desiredStringWidth-availableSpace)
+               }
+       }
+       if DebugHex {
+               log.Debug().Msgf("Actual space %d", availableSpace)
+       }
+
+       z := float64(availableSpace)
+       y := float64(requiredIndexWidth)
+       a := float64(byteWidth)
+       b := float64(quoteRune)
+       // c = needed space for bytes x * byteWidth
+       // x = maxBytesPerRow
+       // x = (z - (y + b + x * 1 + b)) / a == x = (-2 * b - y + z)/(a + 1) 
and a + 1!=0 and a!=0
+       x := ((-2 * b) - y + z) / (a + 1)
+       if DebugHex {
+               log.Debug().Msgf("Calculated number of bytes per row %f in int 
%d", x, int(x))
+       }
+       return int(x), indexDigits
+}
+
 func maskString(data []byte) string {
        for i := range data {
                switch {
diff --git a/plc4go/internal/plc4go/spi/utils/hex_test.go 
b/plc4go/internal/plc4go/spi/utils/hex_test.go
index 2dbe2d1..e8f5cf2 100644
--- a/plc4go/internal/plc4go/spi/utils/hex_test.go
+++ b/plc4go/internal/plc4go/spi/utils/hex_test.go
@@ -19,7 +19,15 @@
 
 package utils
 
-import "testing"
+import (
+       "math"
+       "strings"
+       "testing"
+)
+
+func init() {
+       DebugHex = true
+}
 
 func TestDump(t *testing.T) {
        type args struct {
@@ -35,23 +43,216 @@ func TestDump(t *testing.T) {
                        args: args{
                                data: 
[]byte("1234567890abcdefghijklmnopqrstuvwxyz"),
                        },
-                       want: `000 0x: 31  32  33  34  35  36  37  38  
'12345678'
-008 0x: 39  30  61  62  63  64  65  66  '90abcdef'
-016 0x: 67  68  69  6a  6b  6c  6d  6e  'ghijklmn'
-024 0x: 6f  70  71  72  73  74  75  76  'opqrstuv'
-032 0x: 77  78  79  7a                  'wxyz    '`,
+                       want: `
+00 31  32  33  34  35  36  37  38  39  30  '1234567890'
+10 61  62  63  64  65  66  67  68  69  6a  'abcdefghij'
+20 6b  6c  6d  6e  6f  70  71  72  73  74  'klmnopqrst'
+30 75  76  77  78  79  7a                  'uvwxyz    '
+`,
+               },
+               {
+                       name: "Test Bigger Dump",
+                       args: args{
+                               data: []byte(strings.Repeat("Lorem ipsum", 90)),
+                       },
+                       want: `
+000 4c  6f  72  65  6d  20  69  70  73  75  'Lorem ipsu'
+010 6d  4c  6f  72  65  6d  20  69  70  73  'mLorem ips'
+020 75  6d  4c  6f  72  65  6d  20  69  70  'umLorem ip'
+030 73  75  6d  4c  6f  72  65  6d  20  69  'sumLorem i'
+040 70  73  75  6d  4c  6f  72  65  6d  20  'psumLorem '
+050 69  70  73  75  6d  4c  6f  72  65  6d  'ipsumLorem'
+060 20  69  70  73  75  6d  4c  6f  72  65  ' ipsumLore'
+070 6d  20  69  70  73  75  6d  4c  6f  72  'm ipsumLor'
+080 65  6d  20  69  70  73  75  6d  4c  6f  'em ipsumLo'
+090 72  65  6d  20  69  70  73  75  6d  4c  'rem ipsumL'
+100 6f  72  65  6d  20  69  70  73  75  6d  'orem ipsum'
+110 4c  6f  72  65  6d  20  69  70  73  75  'Lorem ipsu'
+120 6d  4c  6f  72  65  6d  20  69  70  73  'mLorem ips'
+130 75  6d  4c  6f  72  65  6d  20  69  70  'umLorem ip'
+140 73  75  6d  4c  6f  72  65  6d  20  69  'sumLorem i'
+150 70  73  75  6d  4c  6f  72  65  6d  20  'psumLorem '
+160 69  70  73  75  6d  4c  6f  72  65  6d  'ipsumLorem'
+170 20  69  70  73  75  6d  4c  6f  72  65  ' ipsumLore'
+180 6d  20  69  70  73  75  6d  4c  6f  72  'm ipsumLor'
+190 65  6d  20  69  70  73  75  6d  4c  6f  'em ipsumLo'
+200 72  65  6d  20  69  70  73  75  6d  4c  'rem ipsumL'
+210 6f  72  65  6d  20  69  70  73  75  6d  'orem ipsum'
+220 4c  6f  72  65  6d  20  69  70  73  75  'Lorem ipsu'
+230 6d  4c  6f  72  65  6d  20  69  70  73  'mLorem ips'
+240 75  6d  4c  6f  72  65  6d  20  69  70  'umLorem ip'
+250 73  75  6d  4c  6f  72  65  6d  20  69  'sumLorem i'
+260 70  73  75  6d  4c  6f  72  65  6d  20  'psumLorem '
+270 69  70  73  75  6d  4c  6f  72  65  6d  'ipsumLorem'
+280 20  69  70  73  75  6d  4c  6f  72  65  ' ipsumLore'
+290 6d  20  69  70  73  75  6d  4c  6f  72  'm ipsumLor'
+300 65  6d  20  69  70  73  75  6d  4c  6f  'em ipsumLo'
+310 72  65  6d  20  69  70  73  75  6d  4c  'rem ipsumL'
+320 6f  72  65  6d  20  69  70  73  75  6d  'orem ipsum'
+330 4c  6f  72  65  6d  20  69  70  73  75  'Lorem ipsu'
+340 6d  4c  6f  72  65  6d  20  69  70  73  'mLorem ips'
+350 75  6d  4c  6f  72  65  6d  20  69  70  'umLorem ip'
+360 73  75  6d  4c  6f  72  65  6d  20  69  'sumLorem i'
+370 70  73  75  6d  4c  6f  72  65  6d  20  'psumLorem '
+380 69  70  73  75  6d  4c  6f  72  65  6d  'ipsumLorem'
+390 20  69  70  73  75  6d  4c  6f  72  65  ' ipsumLore'
+400 6d  20  69  70  73  75  6d  4c  6f  72  'm ipsumLor'
+410 65  6d  20  69  70  73  75  6d  4c  6f  'em ipsumLo'
+420 72  65  6d  20  69  70  73  75  6d  4c  'rem ipsumL'
+430 6f  72  65  6d  20  69  70  73  75  6d  'orem ipsum'
+440 4c  6f  72  65  6d  20  69  70  73  75  'Lorem ipsu'
+450 6d  4c  6f  72  65  6d  20  69  70  73  'mLorem ips'
+460 75  6d  4c  6f  72  65  6d  20  69  70  'umLorem ip'
+470 73  75  6d  4c  6f  72  65  6d  20  69  'sumLorem i'
+480 70  73  75  6d  4c  6f  72  65  6d  20  'psumLorem '
+490 69  70  73  75  6d  4c  6f  72  65  6d  'ipsumLorem'
+500 20  69  70  73  75  6d  4c  6f  72  65  ' ipsumLore'
+510 6d  20  69  70  73  75  6d  4c  6f  72  'm ipsumLor'
+520 65  6d  20  69  70  73  75  6d  4c  6f  'em ipsumLo'
+530 72  65  6d  20  69  70  73  75  6d  4c  'rem ipsumL'
+540 6f  72  65  6d  20  69  70  73  75  6d  'orem ipsum'
+550 4c  6f  72  65  6d  20  69  70  73  75  'Lorem ipsu'
+560 6d  4c  6f  72  65  6d  20  69  70  73  'mLorem ips'
+570 75  6d  4c  6f  72  65  6d  20  69  70  'umLorem ip'
+580 73  75  6d  4c  6f  72  65  6d  20  69  'sumLorem i'
+590 70  73  75  6d  4c  6f  72  65  6d  20  'psumLorem '
+600 69  70  73  75  6d  4c  6f  72  65  6d  'ipsumLorem'
+610 20  69  70  73  75  6d  4c  6f  72  65  ' ipsumLore'
+620 6d  20  69  70  73  75  6d  4c  6f  72  'm ipsumLor'
+630 65  6d  20  69  70  73  75  6d  4c  6f  'em ipsumLo'
+640 72  65  6d  20  69  70  73  75  6d  4c  'rem ipsumL'
+650 6f  72  65  6d  20  69  70  73  75  6d  'orem ipsum'
+660 4c  6f  72  65  6d  20  69  70  73  75  'Lorem ipsu'
+670 6d  4c  6f  72  65  6d  20  69  70  73  'mLorem ips'
+680 75  6d  4c  6f  72  65  6d  20  69  70  'umLorem ip'
+690 73  75  6d  4c  6f  72  65  6d  20  69  'sumLorem i'
+700 70  73  75  6d  4c  6f  72  65  6d  20  'psumLorem '
+710 69  70  73  75  6d  4c  6f  72  65  6d  'ipsumLorem'
+720 20  69  70  73  75  6d  4c  6f  72  65  ' ipsumLore'
+730 6d  20  69  70  73  75  6d  4c  6f  72  'm ipsumLor'
+740 65  6d  20  69  70  73  75  6d  4c  6f  'em ipsumLo'
+750 72  65  6d  20  69  70  73  75  6d  4c  'rem ipsumL'
+760 6f  72  65  6d  20  69  70  73  75  6d  'orem ipsum'
+770 4c  6f  72  65  6d  20  69  70  73  75  'Lorem ipsu'
+780 6d  4c  6f  72  65  6d  20  69  70  73  'mLorem ips'
+790 75  6d  4c  6f  72  65  6d  20  69  70  'umLorem ip'
+800 73  75  6d  4c  6f  72  65  6d  20  69  'sumLorem i'
+810 70  73  75  6d  4c  6f  72  65  6d  20  'psumLorem '
+820 69  70  73  75  6d  4c  6f  72  65  6d  'ipsumLorem'
+830 20  69  70  73  75  6d  4c  6f  72  65  ' ipsumLore'
+840 6d  20  69  70  73  75  6d  4c  6f  72  'm ipsumLor'
+850 65  6d  20  69  70  73  75  6d  4c  6f  'em ipsumLo'
+860 72  65  6d  20  69  70  73  75  6d  4c  'rem ipsumL'
+870 6f  72  65  6d  20  69  70  73  75  6d  'orem ipsum'
+880 4c  6f  72  65  6d  20  69  70  73  75  'Lorem ipsu'
+890 6d  4c  6f  72  65  6d  20  69  70  73  'mLorem ips'
+900 75  6d  4c  6f  72  65  6d  20  69  70  'umLorem ip'
+910 73  75  6d  4c  6f  72  65  6d  20  69  'sumLorem i'
+920 70  73  75  6d  4c  6f  72  65  6d  20  'psumLorem '
+930 69  70  73  75  6d  4c  6f  72  65  6d  'ipsumLorem'
+940 20  69  70  73  75  6d  4c  6f  72  65  ' ipsumLore'
+950 6d  20  69  70  73  75  6d  4c  6f  72  'm ipsumLor'
+960 65  6d  20  69  70  73  75  6d  4c  6f  'em ipsumLo'
+970 72  65  6d  20  69  70  73  75  6d  4c  'rem ipsumL'
+980 6f  72  65  6d  20  69  70  73  75  6d  'orem ipsum'
+`,
                },
                {
                        name: "minimum size",
                        args: args{
                                []byte("a"),
                        },
-                       want: "000 0x: 61                              'a       
'",
+                       want: "0 61                                      'a     
    '",
+               },
+       }
+       for _, tt := range tests {
+               t.Run(tt.name, func(t *testing.T) {
+                       if got := Dump(tt.args.data); got != 
strings.Trim(tt.want, "\n") {
+                               t.Errorf("Dump() = \n%v\n, want \n%v\n", got, 
tt.want)
+                       }
+               })
+       }
+}
+
+func BenchmarkTestDump(b *testing.B) {
+       DebugHex = false
+       type args struct {
+               data []byte
+       }
+       benchmarks := []struct {
+               name string
+               args args
+       }{
+               {
+                       "small",
+                       args{
+                               data: []byte(strings.Repeat("Lorem ipsum", 1)),
+                       },
+               },
+               {
+                       "medium",
+                       args{
+                               data: []byte(strings.Repeat("Lorem ipsum", 
100)),
+                       },
+               },
+               {
+                       "big",
+                       args{
+                               data: []byte(strings.Repeat("Lorem ipsum", 
10000)),
+                       },
+               },
+       }
+       for _, bm := range benchmarks {
+               b.Run(bm.name, func(b *testing.B) {
+                       for i := 0; i < b.N; i++ {
+                               Dump(bm.args.data)
+                       }
+               })
+       }
+       DebugHex = true
+}
+
+func TestBoxedDump(t *testing.T) {
+       type args struct {
+               name string
+               data []byte
+       }
+       tests := []struct {
+               name string
+               args args
+               want string
+       }{
+               {
+                       name: "Test Dump",
+                       args: args{
+                               name: "super nice data",
+                               data: 
[]byte("1234567890abcdefghijklmnopqrstuvwxyz\3231234567890abcdefghijklmnopqrstuvwxyz\323aa1234567890abcdefghijklmnopqrstuvwxyz\3231234567890abcdefghijklmnopqrstuvwxyz\323aab"),
+                       },
+                       want: `
+╔═super nice data════════════════════════════════════════╗
+║000 31  32  33  34  35  36  37  38  39  30  '1234567890'║
+║010 61  62  63  64  65  66  67  68  69  6a  'abcdefghij'║
+║020 6b  6c  6d  6e  6f  70  71  72  73  74  'klmnopqrst'║
+║030 75  76  77  78  79  7a  d3  31  32  33  'uvwxyz.123'║
+║040 34  35  36  37  38  39  30  61  62  63  '4567890abc'║
+║050 64  65  66  67  68  69  6a  6b  6c  6d  'defghijklm'║
+║060 6e  6f  70  71  72  73  74  75  76  77  'nopqrstuvw'║
+║070 78  79  7a  d3  61  61  31  32  33  34  'xyz.aa1234'║
+║080 35  36  37  38  39  30  61  62  63  64  '567890abcd'║
+║090 65  66  67  68  69  6a  6b  6c  6d  6e  'efghijklmn'║
+║100 6f  70  71  72  73  74  75  76  77  78  'opqrstuvwx'║
+║110 79  7a  d3  31  32  33  34  35  36  37  'yz.1234567'║
+║120 38  39  30  61  62  63  64  65  66  67  '890abcdefg'║
+║130 68  69  6a  6b  6c  6d  6e  6f  70  71  'hijklmnopq'║
+║140 72  73  74  75  76  77  78  79  7a  d3  'rstuvwxyz.'║
+║150 61  61  62                              'aab       '║
+╚════════════════════════════════════════════════════════╝
+`,
                },
        }
        for _, tt := range tests {
                t.Run(tt.name, func(t *testing.T) {
-                       if got := Dump(tt.args.data); got != tt.want {
+                       if got := BoxedDump(tt.args.name, tt.args.data); got != 
strings.Trim(tt.want, "\n") {
                                t.Errorf("Dump() = \n%v\n, want \n%v\n", got, 
tt.want)
                        }
                })
@@ -76,20 +277,84 @@ func TestBoxedDumpFixedWidth(t *testing.T) {
                                data:      
[]byte("1234567890abcdefghijklmnopqrstuvwxyz\3231234567890abcdefghijklmnopqrstuvwxyz\323aa1234567890abcdefghijklmnopqrstuvwxyz\3231234567890abcdefghijklmnopqrstuvwxyz\323aab"),
                                charWidth: 136,
                        },
-                       want: `╔═super nice 
data══════════════════════════════════════════════════════════════════════════════════════════════════════════════════════╗
-║  000 0x: 31  32  33  34  35  36  37  38  39  30  61  62  63  64  65  66  67  
68  69  6a  6b  6c  6d  6e  '1234567890abcdefghijklmn'  ║
-║  024 0x: 6f  70  71  72  73  74  75  76  77  78  79  7a  d3  31  32  33  34  
35  36  37  38  39  30  61  'opqrstuvwxyz.1234567890a'  ║
-║  048 0x: 62  63  64  65  66  67  68  69  6a  6b  6c  6d  6e  6f  70  71  72  
73  74  75  76  77  78  79  'bcdefghijklmnopqrstuvwxy'  ║
-║  072 0x: 7a  d3  61  61  31  32  33  34  35  36  37  38  39  30  61  62  63  
64  65  66  67  68  69  6a  'z.aa1234567890abcdefghij'  ║
-║  096 0x: 6b  6c  6d  6e  6f  70  71  72  73  74  75  76  77  78  79  7a  d3  
31  32  33  34  35  36  37  'klmnopqrstuvwxyz.1234567'  ║
-║  120 0x: 38  39  30  61  62  63  64  65  66  67  68  69  6a  6b  6c  6d  6e  
6f  70  71  72  73  74  75  '890abcdefghijklmnopqrstu'  ║
-║  144 0x: 76  77  78  79  7a  d3  61  61  62                                  
                            'vwxyz.aab               '  ║
-╚══════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════╝`,
+                       want: `
+╔═super nice 
data══════════════════════════════════════════════════════════════════════════════════════════════════════════════════════╗
+║ 000 31  32  33  34  35  36  37  38  39  30  61  62  63  64  65  66  67  68  
69  6a  6b  6c  6d  6e  6f  '1234567890abcdefghijklmno'  ║
+║ 025 70  71  72  73  74  75  76  77  78  79  7a  d3  31  32  33  34  35  36  
37  38  39  30  61  62  63  'pqrstuvwxyz.1234567890abc'  ║
+║ 050 64  65  66  67  68  69  6a  6b  6c  6d  6e  6f  70  71  72  73  74  75  
76  77  78  79  7a  d3  61  'defghijklmnopqrstuvwxyz.a'  ║
+║ 075 61  31  32  33  34  35  36  37  38  39  30  61  62  63  64  65  66  67  
68  69  6a  6b  6c  6d  6e  'a1234567890abcdefghijklmn'  ║
+║ 100 6f  70  71  72  73  74  75  76  77  78  79  7a  d3  31  32  33  34  35  
36  37  38  39  30  61  62  'opqrstuvwxyz.1234567890ab'  ║
+║ 125 63  64  65  66  67  68  69  6a  6b  6c  6d  6e  6f  70  71  72  73  74  
75  76  77  78  79  7a  d3  'cdefghijklmnopqrstuvwxyz.'  ║
+║ 150 61  61  62                                                               
                           'aab                      '  ║
+╚══════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════════╝
+`,
+               },
+       }
+       for _, tt := range tests {
+               t.Run(tt.name, func(t *testing.T) {
+                       if got := BoxedDumpFixedWidth(tt.args.name, 
tt.args.data, tt.args.charWidth); got != strings.Trim(tt.want, "\n") {
+                               t.Errorf("Dump() = \n%v\n, want \n%v\n", got, 
tt.want)
+                       }
+               })
+       }
+}
+
+func TestDumpAnything(t *testing.T) {
+       type args struct {
+               anything interface{}
+       }
+       tests := []struct {
+               name string
+               args args
+               want string
+       }{
+               {
+                       name: "Random struct",
+                       args: args{
+                               anything: struct {
+                                       A string
+                                       B string
+                                       C string
+                                       D struct {
+                                               E string
+                                               F string
+                                       }
+                               }{A: "a", B: "b", C: "c", D: struct {
+                                       E string
+                                       F string
+                               }{
+                                       E: "e",
+                                       F: "f",
+                               }},
+                       },
+                       want: `
+000 25  ff  81  03  01  02  ff  82  00  01  '%.........'
+010 04  01  01  41  01  0c  00  01  01  42  '...A.....B'
+020 01  0c  00  01  01  43  01  0c  00  01  '.....C....'
+030 01  44  01  ff  84  00  00  00  37  ff  '.D......7.'
+040 83  03  01  01  1d  73  74  72  75  63  '.....struc'
+050 74  20  7b  20  45  20  73  74  72  69  't { E stri'
+060 6e  67  3b  20  46  20  73  74  72  69  'ng; F stri'
+070 6e  67  20  7d  01  ff  84  00  01  02  'ng }......'
+080 01  01  45  01  0c  00  01  01  46  01  '..E.....F.'
+090 0c  00  00  00  14  ff  82  01  01  61  '.........a'
+100 01  01  62  01  01  63  01  01  01  65  '..b..c...e'
+110 01  01  66  00  00                      '..f..     '
+`,
+               },
+               {
+                       name: "unexported struct gob error",
+                       args: args{
+                               anything: struct {
+                                       a string
+                               }{a: "a"},
+                       },
+                       want: "<undumpable>",
                },
        }
        for _, tt := range tests {
                t.Run(tt.name, func(t *testing.T) {
-                       if got := BoxedDumpFixedWidth(tt.args.name, 
tt.args.data, tt.args.charWidth); got != tt.want {
+                       if got := DumpAnything(tt.args.anything); got != 
strings.Trim(tt.want, "\n") {
                                t.Errorf("Dump() = \n%v\n, want \n%v\n", got, 
tt.want)
                        }
                })
@@ -112,13 +377,14 @@ func TestDumpFixedWidth(t *testing.T) {
                                data:      
[]byte("1234567890abcdefghijklmnopqrstuvwxyz\3231234567890abcdefghijklmnopqrstuvwxyz\323aa1234567890abcdefghijklmnopqrstuvwxyz\3231234567890abcdefghijklmnopqrstuvwxyz\323aab"),
                                charWidth: 136,
                        },
-                       want: `000 0x: 31  32  33  34  35  36  37  38  39  30  
61  62  63  64  65  66  67  68  69  6a  6b  6c  6d  6e  6f  
'1234567890abcdefghijklmno'
-025 0x: 70  71  72  73  74  75  76  77  78  79  7a  d3  31  32  33  34  35  36 
 37  38  39  30  61  62  63  'pqrstuvwxyz.1234567890abc'
-050 0x: 64  65  66  67  68  69  6a  6b  6c  6d  6e  6f  70  71  72  73  74  75 
 76  77  78  79  7a  d3  61  'defghijklmnopqrstuvwxyz.a'
-075 0x: 61  31  32  33  34  35  36  37  38  39  30  61  62  63  64  65  66  67 
 68  69  6a  6b  6c  6d  6e  'a1234567890abcdefghijklmn'
-100 0x: 6f  70  71  72  73  74  75  76  77  78  79  7a  d3  31  32  33  34  35 
 36  37  38  39  30  61  62  'opqrstuvwxyz.1234567890ab'
-125 0x: 63  64  65  66  67  68  69  6a  6b  6c  6d  6e  6f  70  71  72  73  74 
 75  76  77  78  79  7a  d3  'cdefghijklmnopqrstuvwxyz.'
-150 0x: 61  61  62                                                             
                             'aab                      '`,
+                       want: `
+000 31  32  33  34  35  36  37  38  39  30  61  62  63  64  65  66  67  68  69 
 6a  6b  6c  6d  6e  6f  70  '1234567890abcdefghijklmnop'
+026 71  72  73  74  75  76  77  78  79  7a  d3  31  32  33  34  35  36  37  38 
 39  30  61  62  63  64  65  'qrstuvwxyz.1234567890abcde'
+052 66  67  68  69  6a  6b  6c  6d  6e  6f  70  71  72  73  74  75  76  77  78 
 79  7a  d3  61  61  31  32  'fghijklmnopqrstuvwxyz.aa12'
+078 33  34  35  36  37  38  39  30  61  62  63  64  65  66  67  68  69  6a  6b 
 6c  6d  6e  6f  70  71  72  '34567890abcdefghijklmnopqr'
+104 73  74  75  76  77  78  79  7a  d3  31  32  33  34  35  36  37  38  39  30 
 61  62  63  64  65  66  67  'stuvwxyz.1234567890abcdefg'
+130 68  69  6a  6b  6c  6d  6e  6f  70  71  72  73  74  75  76  77  78  79  7a 
 d3  61  61  62              'hijklmnopqrstuvwxyz.aab   '
+`,
                },
                {
                        name: "minimum size",
@@ -126,12 +392,12 @@ func TestDumpFixedWidth(t *testing.T) {
                                []byte("a"),
                                1,
                        },
-                       want: "000 0x: 61  'a'",
+                       want: "0 61  'a'",
                },
        }
        for _, tt := range tests {
                t.Run(tt.name, func(t *testing.T) {
-                       if got := DumpFixedWidth(tt.args.data, 
tt.args.charWidth); got != tt.want {
+                       if got := DumpFixedWidth(tt.args.data, 
tt.args.charWidth); got != strings.Trim(tt.want, "\n") {
                                t.Errorf("Dump() = \n%v\n, want \n%v\n", got, 
tt.want)
                        }
                })
@@ -166,3 +432,186 @@ func Test_maskString(t *testing.T) {
                })
        }
 }
+
+func Test_MinMax(t *testing.T) {
+       type args struct {
+               data      []byte
+               charWidth int
+       }
+       tests := []struct {
+               name string
+               args args
+               want string
+       }{
+               {
+                       name: "nil data",
+                       args: args{
+                               data:      nil,
+                               charWidth: math.MinInt32,
+                       },
+                       want: "",
+               }, {
+                       name: "empty data",
+                       args: args{
+                               data:      []byte{},
+                               charWidth: math.MinInt32,
+                       },
+                       want: "",
+               },
+               {
+                       name: "-1 one byte",
+                       args: args{
+                               data:      []byte{0x1},
+                               charWidth: -1,
+                       },
+                       want: "0 01  '.'",
+               },
+               {
+                       name: "12",
+               },
+       }
+       for _, tt := range tests {
+               t.Run(tt.name, func(t *testing.T) {
+                       if got := DumpFixedWidth(tt.args.data, 
tt.args.charWidth); got != tt.want {
+                               t.Errorf("maskString() = %v, want %v", got, 
tt.want)
+                       }
+               })
+       }
+}
+
+func Benchmark(b *testing.B) {
+       DebugHex = false
+       type args struct {
+               numberOfBytes, desiredStringWidth int
+       }
+       benchmarks := []struct {
+               name string
+               args args
+       }{
+               {
+                       "small",
+                       args{
+                               numberOfBytes:      1,
+                               desiredStringWidth: 120,
+                       },
+               },
+               {
+                       "medium",
+                       args{
+                               numberOfBytes:      1000,
+                               desiredStringWidth: 120,
+                       },
+               },
+               {
+                       "big",
+                       args{
+                               numberOfBytes:      1000000,
+                               desiredStringWidth: 120,
+                       },
+               },
+       }
+       for _, bm := range benchmarks {
+               b.Run(bm.name, func(b *testing.B) {
+                       for i := 0; i < b.N; i++ {
+                               
calculateBytesPerRowAndIndexWidth(bm.args.numberOfBytes, 
bm.args.desiredStringWidth)
+                       }
+               })
+       }
+       DebugHex = true
+}
+
+func Test_calculateBytesPerRowAndIndexWidth(t *testing.T) {
+       type args struct {
+               numberOfBytes    int
+               desiredCharWidth int
+       }
+       tests := []struct {
+               name               string
+               args               args
+               wantMaxBytesPerRow int
+               wantIndexWidth     int
+       }{
+               {
+                       name: "1 byte MinInt32 width",
+                       args: args{
+                               numberOfBytes:    1,
+                               desiredCharWidth: math.MinInt32,
+                       },
+                       wantMaxBytesPerRow: 1,
+                       wantIndexWidth:     1,
+               },
+               {
+                       name: "10 byte MinInt32 width",
+                       args: args{
+                               numberOfBytes:    10,
+                               desiredCharWidth: math.MinInt32,
+                       },
+                       wantMaxBytesPerRow: 1,
+                       wantIndexWidth:     2,
+               },
+               {
+                       name: "100 byte MinInt32 width",
+                       args: args{
+                               numberOfBytes:    100,
+                               desiredCharWidth: math.MinInt32,
+                       },
+                       wantMaxBytesPerRow: 1,
+                       wantIndexWidth:     3,
+               },
+               {
+                       name: "100 byte MaxInt32 width",
+                       args: args{
+                               numberOfBytes:    100,
+                               desiredCharWidth: math.MaxInt32,
+                       },
+                       wantMaxBytesPerRow: 429496728,
+                       wantIndexWidth:     3,
+               },
+               {
+                       name: "100 byte 12 width",
+                       args: args{
+                               numberOfBytes:    100,
+                               desiredCharWidth: 12,
+                       },
+                       wantMaxBytesPerRow: 1,
+                       wantIndexWidth:     3,
+               },
+               {
+                       name: "153 byte 136 width",
+                       args: args{
+                               numberOfBytes:    153,
+                               desiredCharWidth: 136,
+                       },
+                       wantMaxBytesPerRow: 26,
+                       wantIndexWidth:     3,
+               },
+               {
+                       name: "153 byte calculated width",
+                       args: args{
+                               numberOfBytes: 153,
+                               desiredCharWidth: func() int {
+                                       const quoteRune = 1
+                                       const numberOfBytes = 153
+                                       const indexWidth = 3
+                                       const charRepresentation = 1
+
+                                       // 000 AF FE AF FE ..... '....*'
+                                       return indexWidth + blankWidth + 
(numberOfBytes * byteWidth) + quoteRune + (numberOfBytes * charRepresentation) 
+ quoteRune
+                               }(),
+                       },
+                       wantMaxBytesPerRow: 153,
+                       wantIndexWidth:     3,
+               },
+       }
+       for _, tt := range tests {
+               t.Run(tt.name, func(t *testing.T) {
+                       got, got1 := 
calculateBytesPerRowAndIndexWidth(tt.args.numberOfBytes, 
tt.args.desiredCharWidth)
+                       if got != tt.wantMaxBytesPerRow {
+                               t.Errorf("calculateBytesPerRowAndIndexWidth() 
got max bytes per row = %v, want %v", got, tt.wantMaxBytesPerRow)
+                       }
+                       if got1 != tt.wantIndexWidth {
+                               t.Errorf("calculateBytesPerRowAndIndexWidth() 
got index width = %v, want %v", got1, tt.wantIndexWidth)
+                       }
+               })
+       }
+}

Reply via email to