diff --git a/encoding/gsm7.go b/encoding/gsm7.go index 36fdbe1..3d558a1 100644 --- a/encoding/gsm7.go +++ b/encoding/gsm7.go @@ -2,17 +2,52 @@ package encoding import ( "bytes" - "log" + "fmt" ) type GSM7Coder struct{} -func (c *GSM7Coder) Encode(s string, buf *bytes.Buffer) { - utf8 := []byte(s) - log.Println(utf8) - buf.Write(utf8) +var masks = []byte{ + 0b00000000, + 0b00000001, + 0b00000011, + 0b00000111, + 0b00001111, + 0b00011111, + 0b00111111, + 0b01111111, + 0b11111111, } -func (c *GSM7Coder) Decode(buf *bytes.Buffer) string { - return buf.String() +func (c *GSM7Coder) Encode(s string, buf *bytes.Buffer) error { + // utf8 := *(*[]byte)(unsafe.Pointer(&s)) + utf8 := []byte(s) + var offset byte = 1 + var bitshift byte = 1 + + for index, septet := range utf8 { + if septet > 0b01111111 { + return fmt.Errorf("invalid character at index %d", index) + } + bindex := byte(index) + if bindex == 0 { + continue + } + mask := masks[bitshift] + masked := (mask & septet) << (8 - bitshift) + utf8[bindex-offset] |= masked + utf8[bindex] >>= bitshift + + buf.WriteByte(utf8[bindex-offset]) + bitshift++ + if utf8[bindex] == 0 { + offset++ + bitshift = 1 + } + } + return nil +} + +func (c *GSM7Coder) Decode(buf *bytes.Buffer) (string, error) { + return buf.String(), nil } diff --git a/encoding/gsm7_test.go b/encoding/gsm7_test.go index 1efe42a..166fcfc 100644 --- a/encoding/gsm7_test.go +++ b/encoding/gsm7_test.go @@ -10,8 +10,12 @@ func TestGSM7EncodeSimpleASCIIString(t *testing.T) { var buf bytes.Buffer input := "Sunshine" - expected := []byte{0b11010011, 0b10111001, 0b10111011, 0b10001110, 0b01001110, 0b10111011, 0b11001011} - coder.Encode(input, &buf) + expected := []byte{0b11010011, 0b10111010, 0b01111011, 0b10001110, 0b01001110, 0b10111011, 0b11001011} + err := coder.Encode(input, &buf) + + if err != nil { + t.Errorf("Expected no error, but got %v", err) + } if !bytes.Equal(buf.Bytes(), expected) { t.Errorf("Expected %v, but got %v", expected, buf.Bytes()) @@ -21,11 +25,15 @@ func TestGSM7EncodeSimpleASCIIString(t *testing.T) { func TestGSM7DecodeSimpleASCIIString(t *testing.T) { coder := &GSM7Coder{} var buf bytes.Buffer - input := []byte{0b11010011, 0b10111001, 0b10111011, 0b10001110, 0b01001110, 0b10111011, 0b11001011} + input := []byte{0b11010011, 0b10111010, 0b01111011, 0b10001110, 0b01001110, 0b10111011, 0b11001011} expected := "Sunshine" buf.Write(input) - output := coder.Decode(&buf) + output, err := coder.Decode(&buf) + + if err != nil { + t.Errorf("Expected no error, but got %v", err) + } if output != expected { t.Errorf("Expected %v, but got %v", expected, output) @@ -38,7 +46,11 @@ func TestGSM7EncodeEmptyString(t *testing.T) { input := "" expected := []byte{} - coder.Encode(input, &buf) + err := coder.Encode(input, &buf) + + if err != nil { + t.Errorf("Expected no error, but got %v", err) + } if !bytes.Equal(buf.Bytes(), expected) { t.Errorf("Expected %v, but got %v", expected, buf.Bytes()) @@ -50,7 +62,11 @@ func TestGSM7DecodeEmptyString(t *testing.T) { buf := bytes.NewBuffer([]byte{}) expected := "" - output := coder.Decode(buf) + output, err := coder.Decode(buf) + + if err != nil { + t.Errorf("Expected no error, but got %v", err) + } if output != expected { t.Errorf("Expected %v, but got %v", expected, output)