89 p->encoffset = PWDS_HEADER_SIZE; |
89 p->encoffset = PWDS_HEADER_SIZE; |
90 return p; |
90 return p; |
91 } |
91 } |
92 |
92 |
93 static int readval(UcxBuffer *in, char **val, int allowzero) { |
93 static int readval(UcxBuffer *in, char **val, int allowzero) { |
|
94 // value = length string |
|
95 // length = uint32 |
|
96 // string = bytes |
|
97 |
94 *val = NULL; |
98 *val = NULL; |
|
99 |
|
100 // get length |
95 uint32_t length = 0; |
101 uint32_t length = 0; |
96 if(ucx_buffer_read(&length, 1, sizeof(uint32_t), in) != sizeof(uint32_t)) { |
102 if(ucx_buffer_read(&length, 1, sizeof(uint32_t), in) != sizeof(uint32_t)) { |
97 return 0; |
103 return 0; |
98 } |
104 } |
99 length = ntohl(length); |
105 length = ntohl(length); // convert from BE to host byte order |
100 if(length == 0) { |
106 if(length == 0) { |
101 if(allowzero) { |
107 if(allowzero) { |
102 return 1; |
108 return 1; |
103 } else { |
109 } else { |
104 return 0; |
110 return 0; |
118 *val = value; |
125 *val = value; |
119 return 1; |
126 return 1; |
120 } |
127 } |
121 |
128 |
122 static int read_indexentry(PwdStore *p, UcxBuffer *in) { |
129 static int read_indexentry(PwdStore *p, UcxBuffer *in) { |
|
130 // read type of index element |
123 int type = ucx_buffer_getc(in); |
131 int type = ucx_buffer_getc(in); |
124 if(type == EOF || type != 0) { |
132 if(type == EOF || type != 0) { |
125 // only type 0 supported yet |
133 // only type 0 supported yet |
126 return 0; |
134 return 0; |
127 } |
135 } |
128 |
136 |
129 char *id = NULL; |
137 char *id = NULL; |
130 UcxList *locations = NULL; |
138 UcxList *locations = NULL; |
131 |
139 |
|
140 // get id (required) |
132 int ret = 0; |
141 int ret = 0; |
133 if(readval(in, &id, FALSE)) { |
142 if(readval(in, &id, FALSE)) { |
134 ret = 1; |
143 ret = 1; |
|
144 // get locations |
135 char *location = NULL; |
145 char *location = NULL; |
136 while((ret = readval(in, &location, TRUE)) == 1) { |
146 while((ret = readval(in, &location, TRUE)) == 1) { |
137 if(!location) { |
147 if(!location) { |
138 break; |
148 break; |
139 } |
149 } |
181 return ret; |
191 return ret; |
182 } |
192 } |
183 |
193 |
184 int pwdstore_getindex(PwdStore *s) { |
194 int pwdstore_getindex(PwdStore *s) { |
185 uint32_t netindexlen; |
195 uint32_t netindexlen; |
|
196 |
|
197 // set the position to the last 4 bytes of the header |
|
198 // for reading index length |
186 s->content->pos = PWDS_HEADER_SIZE - sizeof(uint32_t); |
199 s->content->pos = PWDS_HEADER_SIZE - sizeof(uint32_t); |
|
200 |
|
201 // read indexlen and convert to host byte order |
187 if(ucx_buffer_read(&netindexlen, 1, sizeof(uint32_t), s->content) != sizeof(uint32_t)) { |
202 if(ucx_buffer_read(&netindexlen, 1, sizeof(uint32_t), s->content) != sizeof(uint32_t)) { |
188 return 1; |
203 return 1; |
189 } |
204 } |
190 uint32_t indexlen = ntohl(netindexlen); |
205 uint32_t indexlen = ntohl(netindexlen); |
|
206 |
|
207 // integer overflow check |
191 if(UINT32_MAX - PWDS_HEADER_SIZE < indexlen) { |
208 if(UINT32_MAX - PWDS_HEADER_SIZE < indexlen) { |
192 return 1; |
209 return 1; |
193 } |
210 } |
194 if(s->content->size < PWDS_HEADER_SIZE + indexlen) { |
211 if(s->content->size < PWDS_HEADER_SIZE + indexlen) { |
195 return 1; |
212 return 1; |
196 } |
213 } |
197 s->encoffset += indexlen; |
214 // encrypted content starts after the index content |
198 |
215 s->encoffset = PWDS_HEADER_SIZE + indexlen; |
|
216 |
|
217 // the index starts after the header |
199 UcxBuffer *index = ucx_buffer_new(s->content->space+PWDS_HEADER_SIZE, indexlen, 0); |
218 UcxBuffer *index = ucx_buffer_new(s->content->space+PWDS_HEADER_SIZE, indexlen, 0); |
200 index->size = indexlen; |
219 index->size = indexlen; |
|
220 |
|
221 // read index |
201 while(read_indexentry(s, index)) {} |
222 while(read_indexentry(s, index)) {} |
202 |
223 |
|
224 // free index buffer structure (not the content) |
203 ucx_buffer_free(index); |
225 ucx_buffer_free(index); |
204 |
226 |
205 return 0; |
227 return 0; |
206 } |
228 } |
207 |
229 |