]> code.ossystems Code Review - openembedded-core.git/blob
adbe7dfff4b57b2f745735f19592bb6a4c91a760
[openembedded-core.git] /
1 From 8a6e43726ad0ae41bd1cc2c248d91deb31459357 Mon Sep 17 00:00:00 2001
2 From: Lei Maohui <leimaohui@cn.fujitsu.com>
3 Date: Tue, 9 Jun 2015 11:11:48 +0900
4 Subject: [PATCH] packlib.c: support dictionary byte order dependent
5
6 The previous dict files are NOT byte-order independent, in fact they are
7 probably ARCHITECTURE SPECIFIC.
8 Create the dict files in big endian, and convert to host endian while
9 load them. This could fix the endian issue on multiple platform.
10
11 Signed-off-by: Hongxu Jia <hongxu.jia@windriver.com>
12 Upstream-Status: Pending
13
14 We can't use the endian.h, htobe* and be*toh functions because they are
15 not available on older versions of glibc, such as that found in RHEL
16 5.9.
17
18 Change to checking endian and directly calling bswap_* as defined in
19 byteswap.h.
20
21 Signed-off-by: Mark Hatle <mark.hatle@windriver.com>
22
23 Signed-off-by: Lei Maohui <leimaohui@cn.fujitsu.com>
24 ---
25  lib/packlib.c | 214 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++--
26  1 file changed, 210 insertions(+), 4 deletions(-)
27
28 diff --git a/lib/packlib.c b/lib/packlib.c
29 index f851424..3aac805 100644
30 --- a/lib/packlib.c
31 +++ b/lib/packlib.c
32 @@ -16,6 +16,12 @@
33  #ifdef HAVE_STDINT_H
34  #include <stdint.h>
35  #endif
36 +
37 +#ifndef _BSD_SOURCE
38 +#define _BSD_SOURCE             /* See feature_test_macros(7) */
39 +#endif
40 +#include <endian.h>
41 +#include <byteswap.h>
42  #include "packer.h"
43  
44  static const char vers_id[] = "packlib.c : v2.3p2 Alec Muffett 18 May 1993";
45 @@ -45,6 +51,185 @@ typedef struct
46      char data_get[NUMWORDS][MAXWORDLEN];
47  } PWDICT64;
48  
49 +enum{
50 +    en_is32,
51 +    en_is64
52 +};
53 +
54 +static int
55 +IheaderHostToBigEndian(char *pHeader, int nBitType)
56 +{
57 +    if (nBitType == en_is64 && __BYTE_ORDER == __LITTLE_ENDIAN)
58 +    {
59 +        struct pi_header64 *pHeader64 = (struct pi_header64*)pHeader;
60 +
61 +        pHeader64->pih_magic = bswap_64(pHeader64->pih_magic);
62 +        pHeader64->pih_numwords = bswap_64(pHeader64->pih_numwords);
63 +        pHeader64->pih_blocklen = bswap_16(pHeader64->pih_blocklen);
64 +        pHeader64->pih_pad = bswap_16(pHeader64->pih_pad);
65 +
66 +#if DEBUG
67 +        printf("Header64: magic %x, numwords %x, blocklen %x, pad %x\n",
68 +          pHeader64->pih_magic, pHeader64->pih_numwords,
69 +          pHeader64->pih_blocklen, pHeader64->pih_pad);
70 +#endif
71 +    }
72 +    else if (nBitType == en_is32 && __BYTE_ORDER == __LITTLE_ENDIAN)
73 +    {
74 +        struct pi_header *pHeader32 = (struct pi_header*)pHeader;
75 +
76 +        pHeader32->pih_magic = bswap_32(pHeader32->pih_magic);
77 +        pHeader32->pih_numwords = bswap_32(pHeader32->pih_numwords);
78 +        pHeader32->pih_blocklen = bswap_16(pHeader32->pih_blocklen);
79 +        pHeader32->pih_pad = bswap_16(pHeader32->pih_pad);
80 +
81 +#if DEBUG
82 +        printf("Header32: magic %x, numwords %x, blocklen %x, pad %x\n",
83 +          pHeader32->pih_magic, pHeader32->pih_numwords,
84 +          pHeader32->pih_blocklen, pHeader32->pih_pad);
85 +#endif
86 +    }
87 +    else if (__BYTE_ORDER == __LITTLE_ENDIAN)
88 +    {
89 +        fprintf(stderr, "Neither 32 or 64: %d\n", nBitType);
90 +        return (-1);
91 +    }
92 +
93 +    return 0;
94 +}
95 +
96 +static int
97 +IheaderBigEndianToHost(char *pHeader, int nBitType)
98 +{
99 +    if (nBitType == en_is64 && __BYTE_ORDER == __LITTLE_ENDIAN)
100 +    {
101 +        struct pi_header64 *pHeader64 = (struct pi_header64*)pHeader;
102 +
103 +        pHeader64->pih_magic = bswap_64(pHeader64->pih_magic);
104 +        pHeader64->pih_numwords = bswap_64(pHeader64->pih_numwords);
105 +        pHeader64->pih_blocklen = bswap_16(pHeader64->pih_blocklen);
106 +        pHeader64->pih_pad = bswap_16(pHeader64->pih_pad);
107 +
108 +#if DEBUG
109 +        printf("Header64: magic %x, numwords %x, blocklen %x, pad %x\n",
110 +          pHeader64->pih_magic, pHeader64->pih_numwords,
111 +          pHeader64->pih_blocklen, pHeader64->pih_pad);
112 +#endif
113 +    }
114 +    else if (nBitType == en_is32 && __BYTE_ORDER == __LITTLE_ENDIAN)
115 +    {
116 +        struct pi_header *pHeader32 = (struct pi_header*)pHeader;
117 +
118 +        pHeader32->pih_magic = bswap_32(pHeader32->pih_magic);
119 +        pHeader32->pih_numwords = bswap_32(pHeader32->pih_numwords);
120 +        pHeader32->pih_blocklen = bswap_16(pHeader32->pih_blocklen);
121 +        pHeader32->pih_pad = bswap_16(pHeader32->pih_pad);
122 +
123 +#if DEBUG
124 +        printf("Header32: magic %x, numwords %x, blocklen %x, pad %x\n",
125 +            pHeader32->pih_magic, pHeader32->pih_numwords,
126 +            pHeader32->pih_blocklen, pHeader32->pih_pad);
127 +#endif
128 +    }
129 +    else if (__BYTE_ORDER == __LITTLE_ENDIAN)
130 +    {
131 +        fprintf(stderr, "Neither 32 or 64: %d\n", nBitType);
132 +        return (-1);
133 +    }
134 +
135 +    return 0;
136 +}
137 +
138 +static int
139 +HwmsHostToBigEndian(char *pHwms, int nLen,int nBitType)
140 +{
141 +    int i = 0;
142 +
143 +    if (nBitType == en_is64 && __BYTE_ORDER == __LITTLE_ENDIAN)
144 +    {
145 +        uint64_t *pHwms64 = (uint64_t*)pHwms;
146 +
147 +        for (i = 0; i < nLen / sizeof(uint64_t); i++)
148 +        {
149 +            *pHwms64 = bswap_64(*pHwms64);
150 +            *pHwms64++;
151 +        }
152 +
153 +    }
154 +    else if (nBitType == en_is32 && __BYTE_ORDER == __LITTLE_ENDIAN)
155 +    {
156 +        uint32_t *pHwms32 = (uint32_t*)pHwms;
157 +
158 +        for (i = 0; i < nLen / sizeof(uint32_t); i++)
159 +        {
160 +            *pHwms32 = bswap_32(*pHwms32);
161 +            *pHwms32++;
162 +        }
163 +
164 +    }
165 +    else if (__BYTE_ORDER == __LITTLE_ENDIAN)
166 +    {
167 +        fprintf(stderr, "Neither 32 or 64: %d\n", nBitType);
168 +        return (-1);
169 +    }
170 +
171 +#if DEBUG
172 +    for (i = 0; i < nLen; i+=8)
173 +    {
174 +        printf("hwms%s: %02X %02X %02X %02X %02X %02X %02X %02X\n",
175 +            nBitType==en_is64?"64":"32", pHwms[i+0]&0xFF, pHwms[i+1]&0xFF,
176 +            pHwms[i+2]&0xFF, pHwms[i+3]&0xFF, pHwms[i+4]&0xFF,
177 +            pHwms[i+5]&0xFF, pHwms[i+6]&0xFF, pHwms[i+7]&0xFF);
178 +    }
179 +#endif
180 +
181 +    return 0;
182 +}
183 +
184 +static int
185 +HwmsBigEndianToHost(char *pHwms, int nLen, int nBitType)
186 +{
187 +    int i = 0;
188 +
189 +    if (nBitType == en_is64 && __BYTE_ORDER == __LITTLE_ENDIAN)
190 +    {
191 +        uint64_t *pHwms64 = (uint64_t*)pHwms;
192 +
193 +        for (i = 0; i < nLen / sizeof(uint64_t); i++)
194 +        {
195 +            *pHwms64++ = bswap_64(*pHwms64);
196 +        }
197 +
198 +    }
199 +    else if (nBitType == en_is32 && __BYTE_ORDER == __LITTLE_ENDIAN)
200 +    {
201 +        uint32_t *pHwms32 = (uint32_t*)pHwms;
202 +
203 +        for (i = 0; i < nLen / sizeof(uint32_t); i++)
204 +        {
205 +            *pHwms32 = bswap_32(*pHwms32);
206 +            *pHwms32++;
207 +        }
208 +
209 +    }
210 +    else if (__BYTE_ORDER == __LITTLE_ENDIAN)
211 +    {
212 +        fprintf(stderr, "Neither 32 or 64: %d\n", nBitType);
213 +        return (-1);
214 +    }
215 +
216 +#if DEBUG
217 +    for (i = 0; i < nLen; i+=8)
218 +    {
219 +        printf("hwms%s: %02X %02X %02X %02X %02X %02X %02X %02X\n",
220 +            nBitType==en_is64?"64":"32", pHwms[i+0]&0xFF, pHwms[i+1]&0xFF,
221 +            pHwms[i+2]&0xFF, pHwms[i+3]&0xFF, pHwms[i+4]&0xFF,
222 +            pHwms[i+5]&0xFF, pHwms[i+6]&0xFF, pHwms[i+7]&0xFF);
223 +    }
224 +#endif
225 +
226 +    return 0;
227 +}
228  
229  static int
230  _PWIsBroken64(FILE *ifp)
231 @@ -57,6 +242,7 @@ _PWIsBroken64(FILE *ifp)
232         return 0;
233      }
234  
235 +    IheaderBigEndianToHost((char *) &pdesc64.header, en_is64);
236      return (pdesc64.header.pih_magic == PIH_MAGIC);
237  }
238  
239 @@ -149,7 +335,11 @@ PWOpen(prefix, mode)
240         pdesc.header.pih_blocklen = NUMWORDS;
241         pdesc.header.pih_numwords = 0;
242  
243 -       fwrite((char *) &pdesc.header, sizeof(pdesc.header), 1, ifp);
244 +       struct pi_header tmpheader32;
245 +
246 +       memcpy(&tmpheader32,  &pdesc.header, sizeof(pdesc.header));
247 +       IheaderHostToBigEndian((char *) &tmpheader32, en_is32);
248 +       fwrite((char *) &tmpheader32, sizeof(tmpheader32), 1, ifp);
249      } else
250      {
251         pdesc.flags &= ~PFOR_WRITE;
252 @@ -173,6 +363,7 @@ PWOpen(prefix, mode)
253             return NULL;
254         }
255  
256 +        IheaderBigEndianToHost((char *) &pdesc.header, en_is32);
257          if ((pdesc.header.pih_magic == 0) || (pdesc.header.pih_numwords == 0))
258          {
259              /* uh-oh. either a broken "64-bit" file or a garbage file. */
260 @@ -195,6 +386,7 @@ PWOpen(prefix, mode)
261                 }
262                  return NULL;
263              }
264 +            IheaderBigEndianToHost((char *) &pdesc64.header, en_is64);
265              if (pdesc64.header.pih_magic != PIH_MAGIC)
266              {
267                  /* nope, not "64-bit" after all */
268 @@ -290,6 +482,7 @@ PWOpen(prefix, mode)
269                  {
270                      pdesc.flags &= ~PFOR_USEHWMS;
271                  }
272 +                HwmsBigEndianToHost((char*)pdesc64.hwms, sizeof(pdesc64.hwms), en_is64);
273                  for (i = 0; i < sizeof(pdesc.hwms) / sizeof(pdesc.hwms[0]); i++)
274                  {
275                      pdesc.hwms[i] = pdesc64.hwms[i];
276 @@ -299,6 +492,7 @@ PWOpen(prefix, mode)
277             {
278                 pdesc.flags &= ~PFOR_USEHWMS;
279             }
280 +           HwmsBigEndianToHost((char*)pdesc.hwms, sizeof(pdesc.hwms), en_is32);
281  #if DEBUG
282              for (i=1; i<=0xff; i++)
283              {
284 @@ -332,7 +526,11 @@ PWClose(pwp)
285             return (-1);
286         }
287  
288 -       if (!fwrite((char *) &pwp->header, sizeof(pwp->header), 1, pwp->ifp))
289 +       struct pi_header tmpheader32;
290 +
291 +       memcpy(&tmpheader32,  &pwp->header, sizeof(pwp->header));
292 +       IheaderHostToBigEndian((char *) &tmpheader32, en_is32);
293 +       if (!fwrite((char *) &tmpheader32, sizeof(tmpheader32), 1, pwp->ifp))
294         {
295             fprintf(stderr, "index magic fwrite failed\n");
296             return (-1);
297 @@ -351,7 +549,12 @@ PWClose(pwp)
298                 printf("hwm[%02x] = %d\n", i, pwp->hwms[i]);
299  #endif
300             }
301 -           fwrite(pwp->hwms, 1, sizeof(pwp->hwms), pwp->wfp);
302 +
303 +           PWDICT tmp_pwp;
304 +
305 +           memcpy(&tmp_pwp, pwp, sizeof(PWDICT));
306 +           HwmsHostToBigEndian(tmp_pwp.hwms, sizeof(tmp_pwp.hwms), en_is32);
307 +           fwrite(tmp_pwp.hwms, 1, sizeof(tmp_pwp.hwms), pwp->wfp);
308         }
309      }
310  
311 @@ -405,7 +608,8 @@ PutPW(pwp, string)
312  
313         datum = (uint32_t) ftell(pwp->dfp);
314  
315 -       fwrite((char *) &datum, sizeof(datum), 1, pwp->ifp);
316 +       uint32_t tmpdatum = (__BYTE_ORDER == __LITTLE_ENDIAN) ? bswap_32(datum) : datum;
317 +       fwrite((char *) &tmpdatum, sizeof(tmpdatum), 1, pwp->ifp);
318  
319         fputs(pwp->data_put[0], pwp->dfp);
320         putc(0, pwp->dfp);
321 @@ -464,6 +668,7 @@ GetPW(pwp, number)
322             perror("(index fread failed)");
323             return NULL;
324         }
325 +       datum64 = (__BYTE_ORDER == __LITTLE_ENDIAN) ? bswap_64(datum64) : datum64;
326         datum = datum64;
327      } else {
328         if (fseek(pwp->ifp, sizeof(struct pi_header) + (thisblock * sizeof(uint32_t)), 0))
329 @@ -477,6 +682,7 @@ GetPW(pwp, number)
330             perror("(index fread failed)");
331             return NULL;
332         }
333 +       datum = (__BYTE_ORDER == __LITTLE_ENDIAN) ? bswap_32(datum) : datum;
334      }
335  
336         int r = 1;
337 -- 
338 1.8.4.2
339