]>
Commit | Line | Data |
---|---|---|
30fdf114 | 1 | /* 7zStream.c -- 7z Stream functions\r |
5ec5a236 | 2 | 2017-04-03 : Igor Pavlov : Public domain */\r |
c4ab09ef LG |
3 | \r |
4 | #include "Precomp.h"\r | |
30fdf114 LG |
5 | \r |
6 | #include <string.h>\r | |
7 | \r | |
c4ab09ef | 8 | #include "7zTypes.h"\r |
30fdf114 | 9 | \r |
5ec5a236 | 10 | SRes SeqInStream_Read2(const ISeqInStream *stream, void *buf, size_t size, SRes errorType)\r |
30fdf114 LG |
11 | {\r |
12 | while (size != 0)\r | |
13 | {\r | |
14 | size_t processed = size;\r | |
5ec5a236 | 15 | RINOK(ISeqInStream_Read(stream, buf, &processed));\r |
30fdf114 LG |
16 | if (processed == 0)\r |
17 | return errorType;\r | |
18 | buf = (void *)((Byte *)buf + processed);\r | |
19 | size -= processed;\r | |
20 | }\r | |
21 | return SZ_OK;\r | |
22 | }\r | |
23 | \r | |
5ec5a236 | 24 | SRes SeqInStream_Read(const ISeqInStream *stream, void *buf, size_t size)\r |
30fdf114 LG |
25 | {\r |
26 | return SeqInStream_Read2(stream, buf, size, SZ_ERROR_INPUT_EOF);\r | |
27 | }\r | |
28 | \r | |
5ec5a236 | 29 | SRes SeqInStream_ReadByte(const ISeqInStream *stream, Byte *buf)\r |
30fdf114 LG |
30 | {\r |
31 | size_t processed = 1;\r | |
5ec5a236 | 32 | RINOK(ISeqInStream_Read(stream, buf, &processed));\r |
30fdf114 LG |
33 | return (processed == 1) ? SZ_OK : SZ_ERROR_INPUT_EOF;\r |
34 | }\r | |
35 | \r | |
5ec5a236 LG |
36 | \r |
37 | \r | |
38 | SRes LookInStream_SeekTo(const ILookInStream *stream, UInt64 offset)\r | |
30fdf114 LG |
39 | {\r |
40 | Int64 t = offset;\r | |
5ec5a236 | 41 | return ILookInStream_Seek(stream, &t, SZ_SEEK_SET);\r |
30fdf114 LG |
42 | }\r |
43 | \r | |
5ec5a236 | 44 | SRes LookInStream_LookRead(const ILookInStream *stream, void *buf, size_t *size)\r |
30fdf114 | 45 | {\r |
c4ab09ef | 46 | const void *lookBuf;\r |
30fdf114 LG |
47 | if (*size == 0)\r |
48 | return SZ_OK;\r | |
5ec5a236 | 49 | RINOK(ILookInStream_Look(stream, &lookBuf, size));\r |
30fdf114 | 50 | memcpy(buf, lookBuf, *size);\r |
5ec5a236 | 51 | return ILookInStream_Skip(stream, *size);\r |
30fdf114 LG |
52 | }\r |
53 | \r | |
5ec5a236 | 54 | SRes LookInStream_Read2(const ILookInStream *stream, void *buf, size_t size, SRes errorType)\r |
30fdf114 LG |
55 | {\r |
56 | while (size != 0)\r | |
57 | {\r | |
58 | size_t processed = size;\r | |
5ec5a236 | 59 | RINOK(ILookInStream_Read(stream, buf, &processed));\r |
30fdf114 LG |
60 | if (processed == 0)\r |
61 | return errorType;\r | |
62 | buf = (void *)((Byte *)buf + processed);\r | |
63 | size -= processed;\r | |
64 | }\r | |
65 | return SZ_OK;\r | |
66 | }\r | |
67 | \r | |
5ec5a236 | 68 | SRes LookInStream_Read(const ILookInStream *stream, void *buf, size_t size)\r |
30fdf114 LG |
69 | {\r |
70 | return LookInStream_Read2(stream, buf, size, SZ_ERROR_INPUT_EOF);\r | |
71 | }\r | |
72 | \r | |
5ec5a236 LG |
73 | \r |
74 | \r | |
75 | #define GET_LookToRead2 CLookToRead2 *p = CONTAINER_FROM_VTBL(pp, CLookToRead2, vt);\r | |
76 | \r | |
77 | static SRes LookToRead2_Look_Lookahead(const ILookInStream *pp, const void **buf, size_t *size)\r | |
30fdf114 LG |
78 | {\r |
79 | SRes res = SZ_OK;\r | |
5ec5a236 | 80 | GET_LookToRead2\r |
30fdf114 | 81 | size_t size2 = p->size - p->pos;\r |
5ec5a236 | 82 | if (size2 == 0 && *size != 0)\r |
30fdf114 LG |
83 | {\r |
84 | p->pos = 0;\r | |
5ec5a236 LG |
85 | p->size = 0;\r |
86 | size2 = p->bufSize;\r | |
87 | res = ISeekInStream_Read(p->realStream, p->buf, &size2);\r | |
30fdf114 LG |
88 | p->size = size2;\r |
89 | }\r | |
5ec5a236 | 90 | if (*size > size2)\r |
30fdf114 LG |
91 | *size = size2;\r |
92 | *buf = p->buf + p->pos;\r | |
93 | return res;\r | |
94 | }\r | |
95 | \r | |
5ec5a236 | 96 | static SRes LookToRead2_Look_Exact(const ILookInStream *pp, const void **buf, size_t *size)\r |
30fdf114 LG |
97 | {\r |
98 | SRes res = SZ_OK;\r | |
5ec5a236 | 99 | GET_LookToRead2\r |
30fdf114 | 100 | size_t size2 = p->size - p->pos;\r |
5ec5a236 | 101 | if (size2 == 0 && *size != 0)\r |
30fdf114 LG |
102 | {\r |
103 | p->pos = 0;\r | |
5ec5a236 LG |
104 | p->size = 0;\r |
105 | if (*size > p->bufSize)\r | |
106 | *size = p->bufSize;\r | |
107 | res = ISeekInStream_Read(p->realStream, p->buf, size);\r | |
30fdf114 LG |
108 | size2 = p->size = *size;\r |
109 | }\r | |
5ec5a236 | 110 | if (*size > size2)\r |
30fdf114 LG |
111 | *size = size2;\r |
112 | *buf = p->buf + p->pos;\r | |
113 | return res;\r | |
114 | }\r | |
115 | \r | |
5ec5a236 | 116 | static SRes LookToRead2_Skip(const ILookInStream *pp, size_t offset)\r |
30fdf114 | 117 | {\r |
5ec5a236 | 118 | GET_LookToRead2\r |
30fdf114 LG |
119 | p->pos += offset;\r |
120 | return SZ_OK;\r | |
121 | }\r | |
122 | \r | |
5ec5a236 | 123 | static SRes LookToRead2_Read(const ILookInStream *pp, void *buf, size_t *size)\r |
30fdf114 | 124 | {\r |
5ec5a236 | 125 | GET_LookToRead2\r |
30fdf114 LG |
126 | size_t rem = p->size - p->pos;\r |
127 | if (rem == 0)\r | |
5ec5a236 | 128 | return ISeekInStream_Read(p->realStream, buf, size);\r |
30fdf114 LG |
129 | if (rem > *size)\r |
130 | rem = *size;\r | |
131 | memcpy(buf, p->buf + p->pos, rem);\r | |
132 | p->pos += rem;\r | |
133 | *size = rem;\r | |
134 | return SZ_OK;\r | |
135 | }\r | |
136 | \r | |
5ec5a236 | 137 | static SRes LookToRead2_Seek(const ILookInStream *pp, Int64 *pos, ESzSeek origin)\r |
30fdf114 | 138 | {\r |
5ec5a236 | 139 | GET_LookToRead2\r |
30fdf114 | 140 | p->pos = p->size = 0;\r |
5ec5a236 | 141 | return ISeekInStream_Seek(p->realStream, pos, origin);\r |
30fdf114 LG |
142 | }\r |
143 | \r | |
5ec5a236 | 144 | void LookToRead2_CreateVTable(CLookToRead2 *p, int lookahead)\r |
30fdf114 | 145 | {\r |
5ec5a236 LG |
146 | p->vt.Look = lookahead ?\r |
147 | LookToRead2_Look_Lookahead :\r | |
148 | LookToRead2_Look_Exact;\r | |
149 | p->vt.Skip = LookToRead2_Skip;\r | |
150 | p->vt.Read = LookToRead2_Read;\r | |
151 | p->vt.Seek = LookToRead2_Seek;\r | |
30fdf114 LG |
152 | }\r |
153 | \r | |
30fdf114 | 154 | \r |
5ec5a236 LG |
155 | \r |
156 | static SRes SecToLook_Read(const ISeqInStream *pp, void *buf, size_t *size)\r | |
30fdf114 | 157 | {\r |
5ec5a236 | 158 | CSecToLook *p = CONTAINER_FROM_VTBL(pp, CSecToLook, vt);\r |
30fdf114 LG |
159 | return LookInStream_LookRead(p->realStream, buf, size);\r |
160 | }\r | |
161 | \r | |
162 | void SecToLook_CreateVTable(CSecToLook *p)\r | |
163 | {\r | |
5ec5a236 | 164 | p->vt.Read = SecToLook_Read;\r |
30fdf114 LG |
165 | }\r |
166 | \r | |
5ec5a236 | 167 | static SRes SecToRead_Read(const ISeqInStream *pp, void *buf, size_t *size)\r |
30fdf114 | 168 | {\r |
5ec5a236 LG |
169 | CSecToRead *p = CONTAINER_FROM_VTBL(pp, CSecToRead, vt);\r |
170 | return ILookInStream_Read(p->realStream, buf, size);\r | |
30fdf114 LG |
171 | }\r |
172 | \r | |
173 | void SecToRead_CreateVTable(CSecToRead *p)\r | |
174 | {\r | |
5ec5a236 | 175 | p->vt.Read = SecToRead_Read;\r |
30fdf114 | 176 | }\r |