unrarsrc  6.1.7
About: unrar extracts, views and tests the contents of archives created with the RAR archiver.
  Fossies Dox: unrarsrc-6.1.7.tar.gz  ("unofficial" and yet experimental doxygen-generated source code documentation)  

unpackinline.cpp
Go to the documentation of this file.
1_forceinline void Unpack::InsertOldDist(uint Distance)
2{
3 OldDist[3]=OldDist[2];
4 OldDist[2]=OldDist[1];
5 OldDist[1]=OldDist[0];
6 OldDist[0]=Distance;
7}
8
9#ifdef _MSC_VER
10#define FAST_MEMCPY
11#endif
12
13_forceinline void Unpack::CopyString(uint Length,uint Distance)
14{
15 size_t SrcPtr=UnpPtr-Distance;
17 {
18 // If we are not close to end of window, we do not need to waste time
19 // to "& MaxWinMask" pointer protection.
20
21 byte *Src=Window+SrcPtr;
22 byte *Dest=Window+UnpPtr;
23 UnpPtr+=Length;
24
25#ifdef FAST_MEMCPY
26 if (Distance<Length) // Overlapping strings
27#endif
28 while (Length>=8)
29 {
30 Dest[0]=Src[0];
31 Dest[1]=Src[1];
32 Dest[2]=Src[2];
33 Dest[3]=Src[3];
34 Dest[4]=Src[4];
35 Dest[5]=Src[5];
36 Dest[6]=Src[6];
37 Dest[7]=Src[7];
38
39 Src+=8;
40 Dest+=8;
41 Length-=8;
42 }
43#ifdef FAST_MEMCPY
44 else
45 while (Length>=8)
46 {
47 // In theory we still could overlap here.
48 // Supposing Distance == MaxWinSize - 1 we have memcpy(Src, Src + 1, 8).
49 // But for real RAR archives Distance <= MaxWinSize - MAX_INC_LZ_MATCH
50 // always, so overlap here is impossible.
51
52 // This memcpy expanded inline by MSVC. We could also use uint64
53 // assignment, which seems to provide about the same speed.
54 memcpy(Dest,Src,8);
55
56 Src+=8;
57 Dest+=8;
58 Length-=8;
59 }
60#endif
61
62 // Unroll the loop for 0 - 7 bytes left. Note that we use nested "if"s.
63 if (Length>0) { Dest[0]=Src[0];
64 if (Length>1) { Dest[1]=Src[1];
65 if (Length>2) { Dest[2]=Src[2];
66 if (Length>3) { Dest[3]=Src[3];
67 if (Length>4) { Dest[4]=Src[4];
68 if (Length>5) { Dest[5]=Src[5];
69 if (Length>6) { Dest[6]=Src[6]; } } } } } } } // Close all nested "if"s.
70 }
71 else
72 while (Length-- > 0) // Slow copying with all possible precautions.
73 {
74 Window[UnpPtr]=Window[SrcPtr++ & MaxWinMask];
75 // We need to have masked UnpPtr after quit from loop, so it must not
76 // be replaced with 'Window[UnpPtr++ & MaxWinMask]'
78 }
79}
80
81
83{
84 // Left aligned 15 bit length raw bit field.
85 uint BitField=Inp.getbits() & 0xfffe;
86
87 if (BitField<Dec->DecodeLen[Dec->QuickBits])
88 {
89 uint Code=BitField>>(16-Dec->QuickBits);
90 Inp.addbits(Dec->QuickLen[Code]);
91 return Dec->QuickNum[Code];
92 }
93
94 // Detect the real bit length for current code.
95 uint Bits=15;
96 for (uint I=Dec->QuickBits+1;I<15;I++)
97 if (BitField<Dec->DecodeLen[I])
98 {
99 Bits=I;
100 break;
101 }
102
103 Inp.addbits(Bits);
104
105 // Calculate the distance from the start code for current bit length.
106 uint Dist=BitField-Dec->DecodeLen[Bits-1];
107
108 // Start codes are left aligned, but we need the normal right aligned
109 // number. So we shift the distance to the right.
110 Dist>>=(16-Bits);
111
112 // Now we can calculate the position in the code list. It is the sum
113 // of first position for current bit length and right aligned distance
114 // between our bit field and start code for current bit length.
115 uint Pos=Dec->DecodePos[Bits]+Dist;
116
117 // Out of bounds safety check required for damaged archives.
118 if (Pos>=Dec->MaxNum)
119 Pos=0;
120
121 // Convert the position in the code list to position in alphabet
122 // and return it.
123 return Dec->DecodeNum[Pos];
124}
125
126
127_forceinline uint Unpack::SlotToLength(BitInput &Inp,uint Slot)
128{
129 uint LBits,Length=2;
130 if (Slot<8)
131 {
132 LBits=0;
133 Length+=Slot;
134 }
135 else
136 {
137 LBits=Slot/4-1;
138 Length+=(4 | (Slot & 3)) << LBits;
139 }
140
141 if (LBits>0)
142 {
143 Length+=Inp.getbits()>>(16-LBits);
144 Inp.addbits(LBits);
145 }
146 return Length;
147}
uint getbits()
Definition: getbits.hpp:34
void addbits(uint Bits)
Definition: getbits.hpp:25
static const uint MAX_INC_LZ_MATCH
Definition: compress.hpp:17
void CopyString()
void InsertOldDist(unsigned int Distance)
Definition: unpackinline.cpp:1
uint OldDist[4]
Definition: unpack.hpp:249
size_t UnpPtr
Definition: unpack.hpp:256
BitInput Inp
Definition: unpack.hpp:230
byte * Window
Definition: unpack.hpp:271
_forceinline uint SlotToLength(BitInput &Inp, uint Slot)
size_t MaxWinSize
Definition: unpack.hpp:389
_forceinline uint DecodeNumber(BitInput &Inp, DecodeTable *Dec)
size_t MaxWinMask
Definition: unpack.hpp:390
unsigned int uint
Definition: rartypes.hpp:8
uint MaxNum
Definition: unpack.hpp:34
uint QuickBits
Definition: unpack.hpp:49
ushort DecodeNum[LARGEST_TABLE_SIZE]
Definition: unpack.hpp:69
uint DecodePos[16]
Definition: unpack.hpp:45
ushort QuickNum[1<< 10]
Definition: unpack.hpp:59
byte QuickLen[1<< 10]
Definition: unpack.hpp:53
uint DecodeLen[16]
Definition: unpack.hpp:41