Merge pull request #4324 from FernetMenta/wasapi
[vuplus_xbmc] / lib / UnrarXLib / arccmt.cpp
1 bool Archive::GetComment(Array<byte> &CmtData)
2 {
3   if (!MainComment)
4     return(false);
5   SaveFilePos SavePos(*this);
6
7   ushort CmtLength;
8 #ifndef SFX_MODULE
9   if (OldFormat)
10   {
11     Seek(SFXSize+SIZEOF_OLDMHD,SEEK_SET);
12     CmtLength=GetByte()+(GetByte()<<8);
13   }
14   else
15 #endif
16   {
17     if (NewMhd.Flags & MHD_COMMENT)
18     {
19       Seek(SFXSize+SIZEOF_MARKHEAD+SIZEOF_NEWMHD,SEEK_SET);
20       ReadHeader();
21     }
22     else
23     {
24       Seek(SFXSize+SIZEOF_MARKHEAD+NewMhd.HeadSize,SEEK_SET);
25       return(SearchSubBlock(SUBHEAD_TYPE_CMT)!=0 && ReadCommentData(CmtData)!=0);
26     }
27 #ifndef SFX_MODULE
28     if (CommHead.HeadCRC!=HeaderCRC)
29     {
30       Log(FileName,St(MLogCommHead));
31       Alarm();
32       return(false);
33     }
34     CmtLength=CommHead.HeadSize-SIZEOF_COMMHEAD;
35 #endif
36   }
37 #ifndef SFX_MODULE
38   if ((OldFormat && (OldMhd.Flags & MHD_PACK_COMMENT)) || (!OldFormat && CommHead.Method!=0x30))
39   {
40     if (!OldFormat && (CommHead.UnpVer < 15 || CommHead.UnpVer > UNP_VER || CommHead.Method > 0x35))
41       return(false);
42     ComprDataIO DataIO;
43     Unpack Unpack(&DataIO);
44     Unpack.Init();
45     DataIO.SetTestMode(true);
46     uint UnpCmtLength;
47     if (OldFormat)
48     {
49       UnpCmtLength=GetByte()+(GetByte()<<8);
50       CmtLength-=2;
51       DataIO.SetCmt13Encryption();
52     }
53     else
54       UnpCmtLength=CommHead.UnpSize;
55     DataIO.SetFiles(this,NULL);
56     DataIO.EnableShowProgress(false);
57     DataIO.SetPackedSizeToRead(CmtLength);
58     Unpack.SetDestSize(UnpCmtLength);
59     Unpack.DoUnpack(CommHead.UnpVer,false);
60
61     if (!OldFormat && ((~DataIO.UnpFileCRC)&0xffff)!=CommHead.CommCRC)
62     {
63       Log(FileName,St(MLogCommBrk));
64       Alarm();
65       return(false);
66     }
67     else
68     {
69       unsigned char *UnpData;
70       uint UnpDataSize;
71       DataIO.GetUnpackedData(&UnpData,&UnpDataSize);
72       CmtData.Alloc(UnpDataSize);
73       memcpy(&CmtData[0],UnpData,UnpDataSize);
74     }
75   }
76   else
77   {
78     CmtData.Alloc(CmtLength);
79     
80     Read(&CmtData[0],CmtLength);
81     if (!OldFormat && CommHead.CommCRC!=(~CRC(0xffffffff,&CmtData[0],CmtLength)&0xffff))
82     {
83       Log(FileName,St(MLogCommBrk));
84       Alarm();
85       CmtData.Reset();
86       return(false);
87     }
88   }
89 #endif
90 #if defined(_WIN_32) && !defined(_WIN_CE) && !defined(_XBOX) && !defined(_LINUX)
91   if (CmtData.Size()>0)
92     OemToCharBuff((char*)&CmtData[0],(char*)&CmtData[0],CmtData.Size());
93 #endif
94   return(CmtData.Size()>0);
95 }
96
97
98 int Archive::ReadCommentData(Array<byte> &CmtData)
99 {
100   bool Unicode=SubHead.SubFlags & SUBHEAD_FLAGS_CMT_UNICODE;
101   if (!ReadSubData(&CmtData,NULL))
102     return(0);
103   int CmtSize=CmtData.Size();
104   if (Unicode)
105   {
106     CmtSize/=2;
107     Array<wchar> CmtDataW(CmtSize+1);
108     RawToWide(&CmtData[0],&CmtDataW[0],CmtSize);
109     CmtDataW[CmtSize]=0;
110     CmtData.Alloc(CmtSize*2);
111     WideToChar(&CmtDataW[0],(char *)&CmtData[0]);
112     CmtSize=strlen((char *)&CmtData[0]);
113     CmtData.Alloc(CmtSize);
114   }
115   return(CmtSize);
116 }
117
118
119 void Archive::ViewComment()
120 {
121 #ifndef GUI
122   if (Cmd->DisableComment)
123     return;
124   Array<byte> CmtBuf;
125   if (GetComment(CmtBuf))
126   {
127     int CmtSize=CmtBuf.Size();
128     char *ChPtr=(char *)memchr(&CmtBuf[0],0x1A,CmtSize);
129     if (ChPtr!=NULL)
130       CmtSize=ChPtr-(char *)&CmtBuf[0];
131     mprintf("\n");
132     OutComment((char *)&CmtBuf[0],CmtSize);
133   }
134 #endif
135 }
136
137
138 #ifndef SFX_MODULE
139 void Archive::ViewFileComment()
140 {
141   if (!(NewLhd.Flags & LHD_COMMENT) || Cmd->DisableComment || OldFormat)
142     return;
143 #ifndef GUI
144   mprintf(St(MFileComment));
145 #endif
146   const int MaxSize=0x8000;
147   Array<char> CmtBuf(MaxSize);
148   SaveFilePos SavePos(*this);
149   Seek(CurBlockPos+SIZEOF_NEWLHD+NewLhd.NameSize,SEEK_SET);
150   Int64 SaveCurBlockPos=CurBlockPos;
151   Int64 SaveNextBlockPos=NextBlockPos;
152
153   int Size=ReadHeader();
154
155   CurBlockPos=SaveCurBlockPos;
156   NextBlockPos=SaveNextBlockPos;
157
158   if (Size<7 || CommHead.HeadType!=COMM_HEAD)
159     return;
160   if (CommHead.HeadCRC!=HeaderCRC)
161   {
162     #ifndef GUI
163     Log(FileName,St(MLogCommHead));
164 #endif
165     return;
166   }
167   if (CommHead.UnpVer < 15 || CommHead.UnpVer > UNP_VER ||
168       CommHead.Method > 0x30 || CommHead.UnpSize > MaxSize)
169     return;
170   Read(&CmtBuf[0],CommHead.UnpSize);
171   if (CommHead.CommCRC!=((~CRC(0xffffffff,&CmtBuf[0],CommHead.UnpSize)&0xffff)))
172   {
173     Log(FileName,St(MLogBrokFCmt));
174   }
175   else
176   {
177     OutComment(&CmtBuf[0],CommHead.UnpSize);
178 #ifndef GUI
179     mprintf("\n");
180 #endif
181   }
182 }
183 #endif