source: trunk/libdjvu/UnicodeByteStream.cpp @ 426

Last change on this file since 426 was 280, checked in by rbri, 12 years ago

DJVU plugin: djvulibre updated to version 3.5.22

File size: 9.4 KB
Line 
1//C-  -*- C++ -*-
2//C- -------------------------------------------------------------------
3//C- DjVuLibre-3.5
4//C- Copyright (c) 2002  Leon Bottou and Yann Le Cun.
5//C- Copyright (c) 2001  AT&T
6//C-
7//C- This software is subject to, and may be distributed under, the
8//C- GNU General Public License, either Version 2 of the license,
9//C- or (at your option) any later version. The license should have
10//C- accompanied the software or you may obtain a copy of the license
11//C- from the Free Software Foundation at http://www.fsf.org .
12//C-
13//C- This program is distributed in the hope that it will be useful,
14//C- but WITHOUT ANY WARRANTY; without even the implied warranty of
15//C- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16//C- GNU General Public License for more details.
17//C-
18//C- DjVuLibre-3.5 is derived from the DjVu(r) Reference Library from
19//C- Lizardtech Software.  Lizardtech Software has authorized us to
20//C- replace the original DjVu(r) Reference Library notice by the following
21//C- text (see doc/lizard2002.djvu and doc/lizardtech2007.djvu):
22//C-
23//C-  ------------------------------------------------------------------
24//C- | DjVu (r) Reference Library (v. 3.5)
25//C- | Copyright (c) 1999-2001 LizardTech, Inc. All Rights Reserved.
26//C- | The DjVu Reference Library is protected by U.S. Pat. No.
27//C- | 6,058,214 and patents pending.
28//C- |
29//C- | This software is subject to, and may be distributed under, the
30//C- | GNU General Public License, either Version 2 of the license,
31//C- | or (at your option) any later version. The license should have
32//C- | accompanied the software or you may obtain a copy of the license
33//C- | from the Free Software Foundation at http://www.fsf.org .
34//C- |
35//C- | The computer code originally released by LizardTech under this
36//C- | license and unmodified by other parties is deemed "the LIZARDTECH
37//C- | ORIGINAL CODE."  Subject to any third party intellectual property
38//C- | claims, LizardTech grants recipient a worldwide, royalty-free,
39//C- | non-exclusive license to make, use, sell, or otherwise dispose of
40//C- | the LIZARDTECH ORIGINAL CODE or of programs derived from the
41//C- | LIZARDTECH ORIGINAL CODE in compliance with the terms of the GNU
42//C- | General Public License.   This grant only confers the right to
43//C- | infringe patent claims underlying the LIZARDTECH ORIGINAL CODE to
44//C- | the extent such infringement is reasonably necessary to enable
45//C- | recipient to make, have made, practice, sell, or otherwise dispose
46//C- | of the LIZARDTECH ORIGINAL CODE (or portions thereof) and not to
47//C- | any greater extent that may be necessary to utilize further
48//C- | modifications or combinations.
49//C- |
50//C- | The LIZARDTECH ORIGINAL CODE is provided "AS IS" WITHOUT WARRANTY
51//C- | OF ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED
52//C- | TO ANY WARRANTY OF NON-INFRINGEMENT, OR ANY IMPLIED WARRANTY OF
53//C- | MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE.
54//C- +------------------------------------------------------------------
55//
56// $Id: UnicodeByteStream.cpp,v 1.9 2007/03/25 20:48:34 leonb Exp $
57// $Name: release_3_5_22 $
58
59#ifdef HAVE_CONFIG_H
60# include "config.h"
61#endif
62#if NEED_GNUG_PRAGMAS
63# pragma implementation
64#endif
65
66#include "UnicodeByteStream.h"
67#include "ByteStream.h"
68
69
70#ifdef HAVE_NAMESPACES
71namespace DJVU {
72# ifdef NOT_DEFINED // Just to fool emacs c++ mode
73}
74#endif
75#endif
76
77UnicodeByteStream::UnicodeByteStream(const UnicodeByteStream &uni)
78: bs(uni.bs), buffer(uni.buffer), bufferpos(uni.bufferpos), linesread(0)
79{
80  startpos=bs->tell();
81}
82
83UnicodeByteStream::UnicodeByteStream(
84  GP<ByteStream> ibs,const GStringRep::EncodeType et)
85: bs(ibs), bufferpos(0), linesread(0)
86{
87  buffer=GUTF8String::create(0,0,et);
88  startpos=bs->tell();
89}
90
91UnicodeByteStream::~UnicodeByteStream()
92{}
93
94static int
95CountLines(const GUTF8String &str)
96{
97  int retval=0;
98  static const unsigned long lf='\n';
99  for(int pos=0;(pos=str.search(lf,pos)+1)>0;++retval)
100    EMPTY_LOOP;
101  return retval;
102}
103
104void
105UnicodeByteStream::set_encodetype(const GStringRep::EncodeType et)
106{
107  seek(startpos,SEEK_SET);
108  bufferpos=0;
109  buffer=GUTF8String::create(0,0,et);
110}
111
112void
113UnicodeByteStream::set_encoding(const GUTF8String &xencoding)
114{
115  seek(startpos,SEEK_SET);
116  bufferpos=0;
117  buffer=GUTF8String::create(0,0,xencoding);
118}
119
120size_t
121UnicodeByteStream::read(void *buf, size_t size)
122{
123  bufferpos=0;
124  const int retval=bs->read(buf,size);
125  if(retval)
126  {
127    buffer=GUTF8String::create(
128      (unsigned char const *)buf,retval,buffer.get_remainder());
129  }else
130  {
131    buffer=GUTF8String::create(0,0,buffer.get_remainder());
132  }
133  return retval;
134}
135
136size_t
137UnicodeByteStream::write(const void *buf, size_t size)
138{
139  bufferpos=0;
140  buffer=GUTF8String::create(0,0,buffer.get_remainder());
141  return bs->write(buf,size);
142}
143
144long 
145UnicodeByteStream::tell(void) const
146{
147  return bs->tell();
148}
149
150UnicodeByteStream & 
151UnicodeByteStream::operator=(UnicodeByteStream &uni)
152{
153  bs=uni.bs;
154  bufferpos=uni.bufferpos;
155  buffer=uni.buffer;
156  return *this;
157}
158
159int 
160UnicodeByteStream::seek
161(long offset, int whence, bool nothrow)
162{
163  int retval=bs->seek(offset,whence,nothrow);
164  bufferpos=0;
165  buffer=GUTF8String::create(0,0,buffer.get_remainder());
166  return retval;
167}
168
169void 
170UnicodeByteStream::flush(void)
171{
172  bs->flush();
173  bufferpos=0;
174  buffer=GUTF8String::create(0,0,buffer.get_remainder());
175}
176
177
178
179GUTF8String
180UnicodeByteStream::gets(
181  size_t const t,unsigned long const stopat,bool const inclusive)
182{
183  GUTF8String retval;
184  unsigned int len=buffer.length()-bufferpos;
185  if(!len)
186  {
187    int i;
188    char *buf;
189        static const size_t bufsize=327680;
190    GPBuffer<char> gbuf(buf,bufsize);
191    while((i=read(buf,bufsize)>0))
192    {
193      if((len=buffer.length()-bufferpos))
194        break;
195    }
196  }
197  if(len)
198  {
199    int i=buffer.search((char)stopat,bufferpos);
200    if(i>=0)
201    {
202      if(inclusive)
203      {
204        ++i;
205      }
206      if(t&&(i>(int)t+bufferpos))
207      {
208        i=t+bufferpos;
209      }
210      if(i>bufferpos)
211      {
212        retval=buffer.substr(bufferpos,i-bufferpos);
213      }
214      bufferpos=i;
215      linesread+=CountLines(retval);
216    }else
217    {
218      retval=buffer.substr(bufferpos,len);
219      bufferpos=buffer.length();
220      linesread+=CountLines(retval);
221      retval+=gets(t?(t-(i-bufferpos)):0,stopat,inclusive);
222    }
223  }
224  return retval;
225}
226
227XMLByteStream::XMLByteStream(UnicodeByteStream &uni)
228: UnicodeByteStream(uni) {}
229
230XMLByteStream::XMLByteStream(GP<ByteStream> &ibs) 
231: UnicodeByteStream(ibs,GStringRep::XOTHER)
232{}
233
234GP<XMLByteStream>
235XMLByteStream::create(GP<ByteStream> ibs) 
236{
237  XMLByteStream *xml=new XMLByteStream(ibs);
238  GP<XMLByteStream> retval=xml;
239  xml->init();
240  return retval;
241}
242
243void
244XMLByteStream::init(void)
245{
246  unsigned char buf[4];
247  GP<ByteStream> ibs=bs;
248  bufferpos=0;
249  bs->readall(buf,sizeof(buf));
250  const unsigned int i=(buf[0]<<8)+buf[1];
251  switch(i)
252  {
253    case 0x0000:
254    {
255      const unsigned int j=(buf[2]<<8)+buf[3];
256      switch(j)
257      {
258        case 0x003C:
259        {
260          buffer=GUTF8String::create(buf,sizeof(buf),GStringRep::XUCS4BE);
261          break;
262        }
263        case 0x3C00:
264        {
265          buffer=GUTF8String::create(buf,sizeof(buf),GStringRep::XUCS4_2143);
266          break;
267        }
268        case 0xFEFF:
269        {
270          buffer=GUTF8String::create(0,0,GStringRep::XUCS4BE);
271          startpos+=sizeof(buf);
272          break;
273        }
274        case 0xFFFE:
275        {
276          buffer=GUTF8String::create(0,0,GStringRep::XUCS4_2143);
277          startpos+=sizeof(buf);
278          break;
279        }
280        default:
281        {
282          buffer=GUTF8String::create(buf,sizeof(buf),GStringRep::XUTF8);
283          break;
284        }
285      }
286    }
287    case 0x003C:
288    {
289      const unsigned int j=(buf[2]<<8)+buf[3];
290      switch(j)
291      {
292        case 0x0000:
293          buffer=GUTF8String::create(buf,sizeof(buf),GStringRep::XUCS4_3412);
294          break;
295        case 0x003F:
296          buffer=GUTF8String::create(buf,sizeof(buf),GStringRep::XUTF16BE);
297          break;
298        default:
299          buffer=GUTF8String::create(buf,sizeof(buf),GStringRep::XUTF8);
300          break;
301      }
302      break;
303    }
304    case 0x3C00:
305    {
306      const unsigned int j=(buf[2]<<8)+buf[3];
307      switch(j)
308      {
309        case 0x0000:
310          buffer=GUTF8String::create(buf,sizeof(buf),GStringRep::XUCS4LE);
311          break;
312        case 0x3F00:
313          buffer=GUTF8String::create(buf,sizeof(buf),GStringRep::XUTF16LE);
314          break;
315        default:
316          buffer=GUTF8String::create(buf,sizeof(buf),GStringRep::XUTF8);
317          break;
318      }
319      break;
320    }
321    case 0x4C6F:
322    {
323      const unsigned int j=(buf[2]<<8)+buf[3];
324      buffer=GUTF8String::create(buf,sizeof(buf),
325         (j == 0xA794)?(GStringRep::XEBCDIC):(GStringRep::XUTF8));
326      break;
327    }
328    case 0xFFFE:
329    {
330      buffer=GUTF8String::create(buf+2,sizeof(buf)-2,GStringRep::XUTF16LE);
331      startpos+=2;
332      break;
333    }
334    case 0xFEFF:
335    {
336      buffer=GUTF8String::create(buf+2,sizeof(buf)-2,GStringRep::XUTF16BE);
337      startpos+=2;
338      break;
339    }
340    case 0xEFBB:
341    {
342      if(buf[2] == 0xBF)
343      {
344        buffer=GUTF8String::create(buf+3,sizeof(buf)-3,GStringRep::XUTF8);
345        startpos+=3;
346      }else
347      {
348        buffer=GUTF8String::create(buf,sizeof(buf),GStringRep::XUTF8);
349      }
350      break;
351    }
352    case 0x3C3F:
353    default:
354    {
355      buffer=GUTF8String::create(buf,sizeof(buf),GStringRep::XUTF8);
356    }
357  }
358  bs=ibs;
359}
360
361XMLByteStream::~XMLByteStream()
362{}
363
364
365#ifdef HAVE_NAMESPACES
366}
367# ifndef NOT_USING_DJVU_NAMESPACE
368using namespace DJVU;
369# endif
370#endif
Note: See TracBrowser for help on using the repository browser.