bcd

package
v1.1.4 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Jun 12, 2021 License: MIT Imports: 3 Imported by: 12

Documentation

Overview

Package bcd provides functions to encode byte arrays to BCD (Binary-Coded Decimal) encoding and back.

Index

Examples

Constants

This section is empty.

Variables

View Source
var (
	// Standard 8-4-2-1 decimal-only encoding.
	Standard = &BCD{
		Map: map[byte]byte{
			'0': 0x0, '1': 0x1, '2': 0x2, '3': 0x3,
			'4': 0x4, '5': 0x5, '6': 0x6, '7': 0x7,
			'8': 0x8, '9': 0x9,
		},
		SwapNibbles: false,
		Filler:      0xf}

	// Excess-3 or Stibitz encoding.
	Excess3 = &BCD{
		Map: map[byte]byte{
			'0': 0x3, '1': 0x4, '2': 0x5, '3': 0x6,
			'4': 0x7, '5': 0x8, '6': 0x9, '7': 0xa,
			'8': 0xb, '9': 0xc,
		},
		SwapNibbles: false,
		Filler:      0x0}

	// TBCD (Telephony BCD) as in 3GPP TS 29.002.
	Telephony = &BCD{
		Map: map[byte]byte{
			'0': 0x0, '1': 0x1, '2': 0x2, '3': 0x3,
			'4': 0x4, '5': 0x5, '6': 0x6, '7': 0x7,
			'8': 0x8, '9': 0x9, '*': 0xa, '#': 0xb,
			'a': 0xc, 'b': 0xd, 'c': 0xe,
		},
		SwapNibbles: true,
		Filler:      0xf}

	// Aiken or 2421 code
	Aiken = &BCD{
		Map: map[byte]byte{
			'0': 0x0, '1': 0x1, '2': 0x2, '3': 0x3,
			'4': 0x4, '5': 0xb, '6': 0xc, '7': 0xd,
			'8': 0xe, '9': 0xf,
		},
		SwapNibbles: false,
		Filler:      0x5}
)
View Source
var (
	// ErrBadInput returned if input data cannot be encoded.
	ErrBadInput = fmt.Errorf("non-encodable data")
	// ErrBadBCD returned if input data cannot be decoded.
	ErrBadBCD = fmt.Errorf("Bad BCD data")
)

Error values returned by API.

Functions

func DecodedLen

func DecodedLen(x int) int

DecodedLen tells how much space is needed to store decoded string. Please note that it returns the max amount of possibly needed space because last octet may contain only one encoded digit. In that case the decoded length will be less by 1. For example, 4 octets may encode 7 or 8 digits. Please examine the result of Decode to obtain the real value.

func EncodedLen

func EncodedLen(x int) int

EncodedLen returns amount of space needed to store bytes after encoding data of length x.

Types

type BCD

type BCD struct {
	// Map of symbols to encode and decode routines.
	// Example:
	//    key 'a' -> value 0x9
	Map map[byte]byte

	// If true nibbles (4-bit part of a byte) will
	// be swapped, meaning bits 0123 will encode
	// first digit and bits 4567 will encode the
	// second.
	SwapNibbles bool

	// Filler nibble is used if the input has odd
	// number of bytes. Then the output's final nibble
	// will contain the specified nibble.
	Filler byte
}

BCD is the configuration for Binary-Coded Decimal encoding.

type Codec

type Codec struct {
	Encoder
	Decoder
}

Codec encapsulates both Encoder and Decoder.

func NewCodec

func NewCodec(config *BCD) *Codec

NewCodec returns new copy of Codec. See NewEncoder and NewDecoder on behaviour specifics.

type Decoder

type Decoder struct {
	// if the input contains filler nibble in the middle, default
	// behaviour is to treat this as an error. You can tell decoder to
	// resume decoding quietly in that case by setting this.
	IgnoreFiller bool
	// contains filtered or unexported fields
}

Decoder is used to decode BCD converted bytes into decimal string.

Decoder may be copied with no side effects.

func NewDecoder

func NewDecoder(config *BCD) *Decoder

NewDecoder creates new Decoder from BCD configuration. If the configuration is invalid NewDecoder will panic.

func (*Decoder) Decode

func (dec *Decoder) Decode(dst, src []byte) (n int, err error)

Decode parses BCD encoded bytes from src and tries to decode them to dst. Number of decoded bytes and possible error is returned.

Example
dec := NewDecoder(Telephony)

src := []byte{0x21, 0x43, 0xf5}
dst := make([]byte, DecodedLen(len(src)))
n, err := dec.Decode(dst, src)
if err != nil {
	return
}

fmt.Println(string(dst[:n]))
Output:

12345

func (*Decoder) NewReader

func (dec *Decoder) NewReader(rd io.Reader) *Reader

NewReader creates new Reader with underlying io.Reader.

type Encoder

type Encoder struct {
	// contains filtered or unexported fields
}

Encoder is used to encode decimal string into BCD bytes.

Encoder may be copied with no side effects.

func NewEncoder

func NewEncoder(config *BCD) *Encoder

NewEncoder creates new Encoder from BCD configuration. If the configuration is invalid NewEncoder will panic.

func (*Encoder) Encode

func (enc *Encoder) Encode(dst, src []byte) (n int, err error)

Encode get input bytes from src and encodes them into BCD data. Number of encoded bytes and possible error is returned.

Example
enc := NewEncoder(Telephony)

src := []byte("12345")
dst := make([]byte, EncodedLen(len(src)))
n, err := enc.Encode(dst, src)
if err != nil {
	return
}

fmt.Println(bytes.Equal(dst[:n], []byte{0x21, 0x43, 0xf5}))
Output:

true
Example (Second)
enc := NewEncoder(Standard)

src := []byte("1234")
dst := make([]byte, EncodedLen(len(src)))
n, err := enc.Encode(dst, src)
if err != nil {
	return
}

fmt.Println(bytes.Equal(dst[:n], []byte{0x12, 0x34}))
Output:

true

func (*Encoder) NewWriter

func (enc *Encoder) NewWriter(wr io.Writer) *Writer

NewWriter creates new Writer with underlying io.Writer.

type Reader

type Reader struct {
	*Decoder
	// contains filtered or unexported fields
}

Reader reads encoded BCD data from underlying io.Reader and decodes them. Please pay attention that due to ambiguity of encoding process (encoded octet may indicate the end of data by using the filler nibble) the last input octet is not decoded until the next input octet is observed or until underlying io.Reader returns error.

func (*Reader) Read

func (r *Reader) Read(p []byte) (n int, err error)

Read implements io.Reader interface.

type Writer

type Writer struct {
	*Encoder
	// contains filtered or unexported fields
}

Writer encodes input data and writes it to underlying io.Writer. Please pay attention that due to ambiguity of encoding process (encoded octet may indicate the end of data by using the filler nibble) Writer will not write odd remainder of the encoded input data if any until the next octet is observed.

func (*Writer) Buffered

func (w *Writer) Buffered() int

Buffered returns the number of bytes stored in backlog awaiting for its pair.

func (*Writer) Flush

func (w *Writer) Flush() error

Encodes all backlogged data to underlying Writer. If number of bytes is odd, the padding fillers will be applied. Because of this the main usage of Flush is right before stopping Write()-ing data to properly finalize the encoding process.

func (*Writer) Write

func (w *Writer) Write(p []byte) (n int, err error)

Write implements io.Writer interface.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL