Skip to content

Commit fa236eb

Browse files
committed
Merge branch 'develop' into release-1.0.0
2 parents 0e98733 + f456b1e commit fa236eb

13 files changed

Lines changed: 350 additions & 23 deletions

BitByteData.podspec

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,9 +2,9 @@ Pod::Spec.new do |s|
22

33
s.name = "BitByteData"
44
s.version = "1.0.0-test.1"
5-
s.summary = "Read bits and bytes from data consequently in Swift."
5+
s.summary = "Read and write bits and bytes from data consequently in Swift."
66

7-
s.description = "A Swift framework with functions for reading bytes and bits from Data consequently."
7+
s.description = "A Swift framework with functions for reading and writing bytes and bits."
88

99
s.homepage = "https://github.com/tsolomko/BitByteData"
1010
s.documentation_url = "http://tsolomko.github.io/BitByteData"
@@ -22,4 +22,8 @@ Pod::Spec.new do |s|
2222

2323
s.source_files = "Sources/*.swift"
2424

25+
s.test_spec 'Tests' do |test_spec|
26+
test_spec.source_files = 'Tests/BitByteDataTests/*.swift'
27+
end
28+
2529
end

README.md

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -4,11 +4,12 @@
44
[![GitHub license](https://img.shields.io/badge/license-MIT-lightgrey.svg)](https://raw.githubusercontent.com/tsolomko/BitByteData/master/LICENSE)
55
[![Build Status](https://travis-ci.org/tsolomko/BitByteData.svg?branch=develop)](https://travis-ci.org/tsolomko/BitByteData)
66

7-
A Swift framework with classes for reading bytes and bits consequently.
7+
A Swift framework with classes for reading and writing bytes and bits.
88

99
## Installation
1010

1111
Right now only Swift Package manager is supported.
12+
(Carthage and CocoaPods will be available at the 1.0 release).
1213
To install using SPM, add BitByteData to you package dependencies
1314
and specify it as a dependency for your target, e.g.:
1415

@@ -46,7 +47,4 @@ This documentation can be found at its own [website](http://tsolomko.github.io/B
4647
Whether you find a bug, have a suggestion, idea or something else,
4748
please [create an issue](https://github.com/tsolomko/BitByteData/issues) on GitHub.
4849

49-
In case you have encoutered a bug, it would be especially helpful if you attach a file (archive, etc.)
50-
that caused the bug to happen.
51-
5250
If you'd like to contribute code, please [create a pull request](https://github.com/tsolomko/BitByteData/pulls) on GitHub.

Sources/BitReader.swift

Lines changed: 13 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7,18 +7,29 @@ import Foundation
77

88
public protocol BitReader: class {
99

10-
var bitMask: UInt8 { get }
11-
1210
var isAligned: Bool { get }
1311

1412
init(data: Data)
1513

1614
func bits(count: Int) -> [UInt8]
1715

16+
// TODO: Rename?
1817
func intFromBits(count: Int) -> Int
1918

2019
func bit() -> Int
2120

2221
func align()
2322

23+
// TODO: Describe preconditions.
24+
25+
func byte() -> UInt8
26+
27+
func bytes(count: Int) -> [UInt8]
28+
29+
func uint64() -> UInt64
30+
31+
func uint32() -> UInt32
32+
33+
func uint16() -> UInt16
34+
2435
}

Sources/BitWriter.swift

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
// Copyright (c) 2017 Timofey Solomko
2+
// Licensed under MIT License
3+
//
4+
// See LICENSE for license information
5+
6+
import Foundation
7+
8+
public protocol BitWriter {
9+
10+
var data: Data { get }
11+
12+
init()
13+
14+
var isAligned: Bool { get }
15+
16+
func write(bit: UInt8)
17+
18+
func write(bits: [UInt8])
19+
20+
// TODO: Describe, what will happen if `bitsCount` is smaller than actual amount of `number`'s bits.
21+
// TODO: Describe, that `number` is processed in the same order as `BitWriter`'s.
22+
func write(number: Int, bitsCount: Int)
23+
24+
func append(byte: UInt8)
25+
26+
// TODO: Describe, that it doesn't check if it actually needs to align.
27+
func align()
28+
29+
}
30+
31+
extension BitWriter {
32+
33+
public func write(bits: [UInt8]) {
34+
for bit in bits {
35+
self.write(bit: bit)
36+
}
37+
}
38+
39+
}

Sources/LsbBitReader.swift

Lines changed: 1 addition & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -7,17 +7,12 @@ import Foundation
77

88
public final class LsbBitReader: ByteReader, BitReader {
99

10-
public private(set) var bitMask: UInt8
10+
private var bitMask: UInt8 = 1
1111

1212
public var isAligned: Bool {
1313
return self.bitMask == 1
1414
}
1515

16-
public override init(data: Data) {
17-
self.bitMask = 1
18-
super.init(data: data)
19-
}
20-
2116
public func bits(count: Int) -> [UInt8] {
2217
guard count > 0 else {
2318
return []

Sources/LsbBitWriter.swift

Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,54 @@
1+
// Copyright (c) 2017 Timofey Solomko
2+
// Licensed under MIT License
3+
//
4+
// See LICENSE for license information
5+
6+
import Foundation
7+
8+
public final class LsbBitWriter: BitWriter {
9+
10+
public private(set) var data: Data = Data()
11+
12+
private var bitMask: UInt8 = 1
13+
private var currentByte: UInt8 = 0
14+
15+
public var isAligned: Bool {
16+
return self.bitMask == 1
17+
}
18+
19+
public init() { }
20+
21+
public func write(bit: UInt8) {
22+
precondition(bit <= 1, "A bit must be either 0 or 1.")
23+
24+
self.currentByte += self.bitMask * bit
25+
26+
if self.bitMask == 128 {
27+
self.bitMask = 1
28+
self.data.append(self.currentByte)
29+
self.currentByte = 0
30+
} else {
31+
self.bitMask <<= 1
32+
}
33+
}
34+
35+
public func write(number: Int, bitsCount: Int) {
36+
var mask = 1
37+
for _ in 0..<bitsCount {
38+
self.write(bit: number & mask > 0 ? 1 : 0)
39+
mask <<= 1
40+
}
41+
}
42+
43+
public func append(byte: UInt8) {
44+
precondition(isAligned, "BitWriter is not aligned.")
45+
self.data.append(byte)
46+
}
47+
48+
public func align() {
49+
self.data.append(self.currentByte)
50+
self.currentByte = 0
51+
self.bitMask = 1
52+
}
53+
54+
}

Sources/MsbBitReader.swift

Lines changed: 1 addition & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -7,17 +7,12 @@ import Foundation
77

88
public final class MsbBitReader: ByteReader, BitReader {
99

10-
public private(set) var bitMask: UInt8
10+
private var bitMask: UInt8 = 128
1111

1212
public var isAligned: Bool {
1313
return self.bitMask == 128
1414
}
1515

16-
public override init(data: Data) {
17-
self.bitMask = 128
18-
super.init(data: data)
19-
}
20-
2116
public func bits(count: Int) -> [UInt8] {
2217
guard count > 0 else {
2318
return []

Sources/MsbBitWriter.swift

Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,54 @@
1+
// Copyright (c) 2017 Timofey Solomko
2+
// Licensed under MIT License
3+
//
4+
// See LICENSE for license information
5+
6+
import Foundation
7+
8+
public final class MsbBitWriter: BitWriter {
9+
10+
public private(set) var data: Data = Data()
11+
12+
private var bitMask: UInt8 = 128
13+
private var currentByte: UInt8 = 0
14+
15+
public var isAligned: Bool {
16+
return self.bitMask == 128
17+
}
18+
19+
public init() { }
20+
21+
public func write(bit: UInt8) {
22+
precondition(bit <= 1, "A bit must be either 0 or 1.")
23+
24+
self.currentByte += self.bitMask * bit
25+
26+
if self.bitMask == 1 {
27+
self.bitMask = 128
28+
self.data.append(self.currentByte)
29+
self.currentByte = 0
30+
} else {
31+
self.bitMask >>= 1
32+
}
33+
}
34+
35+
public func write(number: Int, bitsCount: Int) {
36+
var mask = 1 << (bitsCount - 1)
37+
for _ in 0..<bitsCount {
38+
self.write(bit: number & mask > 0 ? 1 : 0)
39+
mask >>= 1
40+
}
41+
}
42+
43+
public func append(byte: UInt8) {
44+
precondition(isAligned, "BitWriter is not aligned.")
45+
self.data.append(byte)
46+
}
47+
48+
public func align() {
49+
self.data.append(self.currentByte)
50+
self.currentByte = 0
51+
self.bitMask = 128
52+
}
53+
54+
}

Tests/BitByteDataTests/LsbBitReaderTests.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -76,4 +76,4 @@ class LsbBitReaderTests: XCTestCase {
7676
XCTAssertTrue(bitReader.isAtTheEnd)
7777
}
7878

79-
}
79+
}
Lines changed: 73 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,73 @@
1+
// Copyright (c) 2017 Timofey Solomko
2+
// Licensed under MIT License
3+
//
4+
// See LICENSE for license information
5+
6+
import XCTest
7+
import BitByteData
8+
9+
class LsbBitWriterTests: XCTestCase {
10+
11+
func testWriteBit() {
12+
let bitWriter = LsbBitWriter()
13+
14+
bitWriter.write(bit: 0)
15+
bitWriter.write(bit: 1)
16+
bitWriter.write(bit: 0)
17+
bitWriter.write(bit: 1)
18+
bitWriter.write(bit: 1)
19+
bitWriter.align()
20+
XCTAssertEqual(bitWriter.data, Data(bytes: [26]))
21+
}
22+
23+
func testWriteBitsArray() {
24+
let bitWriter = LsbBitWriter()
25+
26+
bitWriter.write(bits: [1, 1, 0, 0, 1, 0, 1, 0, 0, 1, 1])
27+
bitWriter.align()
28+
XCTAssertEqual(bitWriter.data, Data(bytes: [83, 6]))
29+
}
30+
31+
func testWriteNumber() {
32+
let bitWriter = LsbBitWriter()
33+
34+
bitWriter.write(number: 255, bitsCount: 8)
35+
XCTAssertEqual(bitWriter.data, Data(bytes: [255]))
36+
bitWriter.write(number: 6, bitsCount: 3)
37+
XCTAssertEqual(bitWriter.data, Data(bytes: [255]))
38+
bitWriter.write(number: 103, bitsCount: 7)
39+
XCTAssertEqual(bitWriter.data, Data(bytes: [255, 62]))
40+
bitWriter.align()
41+
XCTAssertEqual(bitWriter.data, Data(bytes: [255, 62, 3]))
42+
}
43+
44+
func testAppendByte() {
45+
let bitWriter = LsbBitWriter()
46+
47+
bitWriter.append(byte: 0xCA)
48+
XCTAssertEqual(bitWriter.data, Data(bytes: [0xCA]))
49+
}
50+
51+
func testFinish() {
52+
let bitWriter = LsbBitWriter()
53+
54+
bitWriter.align()
55+
XCTAssertEqual(bitWriter.data, Data(bytes: [0]))
56+
XCTAssertTrue(bitWriter.isAligned)
57+
}
58+
59+
func testIsAligned() {
60+
let bitWriter = MsbBitWriter()
61+
62+
bitWriter.write(bits: [0, 1, 0])
63+
XCTAssertFalse(bitWriter.isAligned)
64+
bitWriter.write(bits: [0, 1, 0, 1, 0])
65+
XCTAssertTrue(bitWriter.isAligned)
66+
67+
bitWriter.write(bit: 0)
68+
XCTAssertFalse(bitWriter.isAligned)
69+
bitWriter.align()
70+
XCTAssertTrue(bitWriter.isAligned)
71+
}
72+
73+
}

0 commit comments

Comments
 (0)