Update contrib.
1 // Copyright (c) 1996-2009 Nokia Corporation and/or its subsidiary(-ies).
2 // All rights reserved.
3 // This component and the accompanying materials are made available
4 // under the terms of the License "Eclipse Public License v1.0"
5 // which accompanies this distribution, and is available
6 // at the URL "http://www.eclipse.org/legal/epl-v10.html".
8 // Initial Contributors:
9 // Nokia Corporation - initial contribution.
18 #define FILE_ID 0x555A4950
24 const TInt INBUFSIZE = 0x2000;
25 const TUint32 RETRY_WARNING_COUNT = 100; // if we get 100 retries, things must be really bad...
29 #define Z (*TheZipInfo)
35 TUint8 inbuf[INBUFSIZE];
36 TUint8* volatile inptr; /* index of next byte to be processed in inbuf */
37 TUint8* volatile inbuf_end; /* pointer to last valid input byte + 1 */
38 TUint8* volatile outptr; /* pointer to output data */
40 TAny* malloc(TUint aSize)
42 return MALLOC((TInt)aSize);
52 WAIT_FOR_ANY_REQUEST(); // wait for a block from the file
54 TInt avail=(TInt)w-(TInt)Z.iFileBufR;
55 TInt amount=(avail>(TInt)INBUFSIZE)?INBUFSIZE:avail;
56 TInt rix=(TInt)(Z.iFileBufR & (Z.iFileBufSize-1));
57 memcpy(inbuf,Z.iFileBuf+rix,amount);
60 inbuf_end=inbuf+amount;
64 void process_block(int error)
66 AcceptUnzippedBlock(Z, (TUint8*&)outptr, error);
70 const TUint KZipSpan=0x30304b50u;
71 TInt ParseZipHeader(TZipInfo& a)
73 TInt avail=inbuf_end-inptr;
74 if (avail<KZipLocalHeaderLen)
77 TUint sig=*(TUint*)inptr; // OK since at beginning of buffer
80 PrintToScreen(_L("ZIP: Split archive\r\n"));
85 sig=*(TUint*)inptr; // OK since at beginning of buffer
87 if (sig!=KZipSignature)
93 memcpy(&a.iCrc,inptr,12); // crc, comp size, uncomp size
95 a.iFileNameLength=*inptr | (inptr[1]<<8);
97 a.iExtraLength=*inptr | (inptr[1]<<8);
99 if (a.iFlags & (CRPFLG|EXTFLG))
100 return KErrNotSupported;
101 if (a.iMethod!=STORED && a.iMethod!=DEFLATED)
102 return KErrNotSupported;
103 if (avail<KZipLocalHeaderLen+a.iFileNameLength+a.iExtraLength)
106 a.iDataOffset+=a.iFileNameLength+a.iExtraLength;
107 TInt fnamelen=Min(a.iFileNameLength,a.iName.MaxLength());
108 TPtrC8 fileNamePtr(inptr,fnamelen);
109 a.iName.Copy(fileNamePtr);
113 TInt UnzipThread(TAny* aInfo)
115 TheZipInfo=(TZipInfo*)aInfo;
116 Z.iProcessedHeader=KRequestPending;
121 TInt r=ParseZipHeader(Z);
124 inptr=inbuf+Z.iDataOffset;
126 WAIT_FOR_REQUEST(Z.iProcessedHeader);
129 r=UnzipComplete(Z, outptr, r);
133 TInt InitInfo(TZipInfo& a)
135 a.iInBufSize=INBUFSIZE;
139 a.iProcessedHeader=KRequestPending;
143 a.iThreadStatus=KRequestPending;
147 TInt ReadBlockToBuffer(TZipInfo& a, RFile &aBootFile)
149 TInt numAttempts = 0;
151 // If the buffer is full, wait for it to empty before continuing
152 // There is no point exiting after a number of retries because it will the fail later on
153 // So, loop forever if the buffer doesn't empty, but print a warning after the retry count has passed
154 while (a.iFileBufW-a.iFileBufR==a.iFileBufSize)
157 if (numAttempts % RETRY_WARNING_COUNT == 0)
159 PrintToScreen(_L("ZIP: ReadBlockToBuffer stuck waiting for buffer to empty (retry #%d)\r\n"), numAttempts);
161 DELAY(20000); // buffer full so wait a bit
164 TInt req_len=Min(a.iRemain,INBUFSIZE);
166 TInt wix=(TInt)(a.iFileBufW & (a.iFileBufSize-1));
169 r = ReadInputData(a.iFileBuf+wix,len);
175 ImageReadProgress+=len;