aboutsummaryrefslogtreecommitdiff
path: root/src/lzss/lzssencoder.nim
diff options
context:
space:
mode:
Diffstat (limited to 'src/lzss/lzssencoder.nim')
-rw-r--r--src/lzss/lzssencoder.nim16
1 files changed, 7 insertions, 9 deletions
diff --git a/src/lzss/lzssencoder.nim b/src/lzss/lzssencoder.nim
index 82fbe7b..36e0c7e 100644
--- a/src/lzss/lzssencoder.nim
+++ b/src/lzss/lzssencoder.nim
@@ -14,20 +14,18 @@
14# You should have received a copy of the GNU Affero General Public License 14# You should have received a copy of the GNU Affero General Public License
15# along with this program. If not, see <https://www.gnu.org/licenses/>. 15# along with this program. If not, see <https://www.gnu.org/licenses/>.
16 16
17import lists 17import matchtable, lzssnode, lzsschain
18import listpolyfill, matchtable, lzssnode, lzsschain
19 18
20const matchGroupLength* = 3 19const matchGroupLength* = 3
21const maxRefByteLength = high(uint8).int + matchGroupLength 20const maxRefByteLength = high(uint8).int + matchGroupLength
22let emptySinglyLinkedList = initSinglyLinkedList[int]()
23 21
24proc commonPrefixLength*(a, b: openArray[uint8], skipFirst, maxLength: int): int = 22proc commonPrefixLength*(a, b: openArray[uint8], skipFirst, maxLength: int): int =
25 result = skipFirst 23 result = skipFirst
26 let maxPrefixLength = min(min(a.len, b.len), maxLength) 24 let maxPrefixLength = min(min(a.len, b.len), maxLength)
27 while result < maxPrefixLength and a[result] == b[result]: result += 1 25 while result < maxPrefixLength and a[result] == b[result]: result += 1
28 26
29proc longestPrefix*(candidatePos: SinglyLinkedList[int], searchBuf, lookAheadBuf: openArray[uint8]): tuple[length, pos: int] = 27proc longestPrefix*(candidatePos: openArray[int], searchBuf, lookAheadBuf: openArray[uint8]): tuple[length, pos: int] =
30 for startIndex in candidatePos.items: 28 for startIndex in candidatePos:
31 let prefixLength = commonPrefixLength( 29 let prefixLength = commonPrefixLength(
32 searchBuf.toOpenArray(startIndex, searchBuf.len - 1), lookAheadBuf, matchGroupLength, maxRefByteLength) 30 searchBuf.toOpenArray(startIndex, searchBuf.len - 1), lookAheadBuf, matchGroupLength, maxRefByteLength)
33 if prefixLength > result.length: result = (prefixLength, startIndex) 31 if prefixLength > result.length: result = (prefixLength, startIndex)
@@ -39,20 +37,20 @@ proc addGroups*(matchTable: MatchTable[seq[uint8], int], buffer: openArray[uint8
39 matchTable.addMatch(group, cursor) 37 matchTable.addMatch(group, cursor)
40 38
41proc lzssEncode*(buf: openArray[uint8]): LzssChain = 39proc lzssEncode*(buf: openArray[uint8]): LzssChain =
42 result = initSinglyLinkedList[LzssNode]() 40 result = newSeqOfCap[LzssNode](buf.len)
43 let matchTable = initMatchTable(seq[uint8], int) 41 let matchTable = initMatchTable(seq[uint8], int)
44 var cursor = 0 42 var cursor = 0
45 while cursor < buf.len() - matchGroupLength: 43 while cursor < buf.len() - matchGroupLength:
46 let matches = matchTable.matchList(buf[cursor..<(cursor + matchGroupLength)]) 44 let matches = matchTable.matchList(buf[cursor..<(cursor + matchGroupLength)])
47 let prefix = matches.longestPrefix(buf.toOpenArray(0, cursor - 1), buf.toOpenArray(cursor, buf.len - 1)) 45 let prefix = matches.longestPrefix(buf.toOpenArray(0, cursor - 1), buf.toOpenArray(cursor, buf.len - 1))
48 if prefix.length > 0: 46 if prefix.length > 0:
49 result.append(lzssReference(prefix.length, cursor - prefix.pos)) 47 result.add(lzssReference(prefix.length, cursor - prefix.pos))
50 cursor += prefix.length 48 cursor += prefix.length
51 else: 49 else:
52 result.append(lzssCharacter(buf[cursor])) 50 result.add(lzssCharacter(buf[cursor]))
53 cursor += 1 51 cursor += 1
54 if cursor - prefix.length >= matchGroupLength: 52 if cursor - prefix.length >= matchGroupLength:
55 matchTable.addGroups(buf, cursor - prefix.length - matchGroupLength, cursor) 53 matchTable.addGroups(buf, cursor - prefix.length - matchGroupLength, cursor)
56 while cursor < buf.len: 54 while cursor < buf.len:
57 result.append(lzssCharacter(buf[cursor])) 55 result.add(lzssCharacter(buf[cursor]))
58 cursor += 1 56 cursor += 1