1 /**************************************************************
2 *
3 * Licensed to the Apache Software Foundation (ASF) under one
4 * or more contributor license agreements. See the NOTICE file
5 * distributed with this work for additional information
6 * regarding copyright ownership. The ASF licenses this file
7 * to you under the Apache License, Version 2.0 (the
8 * "License"); you may not use this file except in compliance
9 * with the License. You may obtain a copy of the License at
10 *
11 * http://www.apache.org/licenses/LICENSE-2.0
12 *
13 * Unless required by applicable law or agreed to in writing,
14 * software distributed under the License is distributed on an
15 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16 * KIND, either express or implied. See the License for the
17 * specific language governing permissions and limitations
18 * under the License.
19 *
20 *************************************************************/
21
22
23
24 // MARKER(update_precomp.py): autogen include statement, do not remove
25 #include "precompiled_vcl.hxx"
26
27 #include <tools/debug.hxx>
28 #include <tools/stream.hxx>
29
30 #include <rtl/alloc.h>
31
32 #include <vcl/jobset.hxx>
33
34 #include <jobset.h>
35
36 // =======================================================================
37
38 DBG_NAME( JobSetup )
39
40 #define JOBSET_FILEFORMAT2 3780
41 #define JOBSET_FILE364_SYSTEM ((sal_uInt16)0xFFFF)
42 #define JOBSET_FILE605_SYSTEM ((sal_uInt16)0xFFFE)
43
44 struct ImplOldJobSetupData
45 {
46 char cPrinterName[64];
47 char cDeviceName[32];
48 char cPortName[32];
49 char cDriverName[32];
50 };
51
52 struct Impl364JobSetupData
53 {
54 SVBT16 nSize;
55 SVBT16 nSystem;
56 SVBT32 nDriverDataLen;
57 SVBT16 nOrientation;
58 SVBT16 nPaperBin;
59 SVBT16 nPaperFormat;
60 SVBT32 nPaperWidth;
61 SVBT32 nPaperHeight;
62 };
63
64 // =======================================================================
65
ImplJobSetup()66 ImplJobSetup::ImplJobSetup()
67 {
68 mnRefCount = 1;
69 mnSystem = 0;
70 meOrientation = ORIENTATION_PORTRAIT;
71 meDuplexMode = DUPLEX_UNKNOWN;
72 mnPaperBin = 0;
73 mePaperFormat = PAPER_USER;
74 mnPaperWidth = 0;
75 mnPaperHeight = 0;
76 mnDriverDataLen = 0;
77 mpDriverData = NULL;
78 }
79
80 // -----------------------------------------------------------------------
81
ImplJobSetup(const ImplJobSetup & rJobSetup)82 ImplJobSetup::ImplJobSetup( const ImplJobSetup& rJobSetup ) :
83 maPrinterName( rJobSetup.maPrinterName ),
84 maDriver( rJobSetup.maDriver )
85 {
86 mnRefCount = 1;
87 mnSystem = rJobSetup.mnSystem;
88 meOrientation = rJobSetup.meOrientation;
89 meDuplexMode = rJobSetup.meDuplexMode;
90 mnPaperBin = rJobSetup.mnPaperBin;
91 mePaperFormat = rJobSetup.mePaperFormat;
92 mnPaperWidth = rJobSetup.mnPaperWidth;
93 mnPaperHeight = rJobSetup.mnPaperHeight;
94 mnDriverDataLen = rJobSetup.mnDriverDataLen;
95 if ( rJobSetup.mpDriverData )
96 {
97 mpDriverData = (sal_uInt8*)rtl_allocateMemory( mnDriverDataLen );
98 memcpy( mpDriverData, rJobSetup.mpDriverData, mnDriverDataLen );
99 }
100 else
101 mpDriverData = NULL;
102 maValueMap = rJobSetup.maValueMap;
103 }
104
105 // -----------------------------------------------------------------------
106
~ImplJobSetup()107 ImplJobSetup::~ImplJobSetup()
108 {
109 rtl_freeMemory( mpDriverData );
110 }
111
112 // =======================================================================
113
ImplGetData()114 ImplJobSetup* JobSetup::ImplGetData()
115 {
116 if ( !mpData )
117 mpData = new ImplJobSetup;
118 else if ( mpData->mnRefCount != 1 )
119 {
120 mpData->mnRefCount--;
121 mpData = new ImplJobSetup( *mpData );
122 }
123
124 return mpData;
125 }
126
127 // -----------------------------------------------------------------------
128
ImplGetConstData()129 ImplJobSetup* JobSetup::ImplGetConstData()
130 {
131 if ( !mpData )
132 mpData = new ImplJobSetup;
133 return mpData;
134 }
135
136 // -----------------------------------------------------------------------
137
ImplGetConstData() const138 const ImplJobSetup* JobSetup::ImplGetConstData() const
139 {
140 if ( !mpData )
141 ((JobSetup*)this)->mpData = new ImplJobSetup;
142 return mpData;
143 }
144
145 // =======================================================================
146
JobSetup()147 JobSetup::JobSetup()
148 {
149 DBG_CTOR( JobSetup, NULL );
150
151 mpData = NULL;
152 }
153
154 // -----------------------------------------------------------------------
155
JobSetup(const JobSetup & rJobSetup)156 JobSetup::JobSetup( const JobSetup& rJobSetup )
157 {
158 DBG_CTOR( JobSetup, NULL );
159 DBG_CHKOBJ( &rJobSetup, JobSetup, NULL );
160 DBG_ASSERT( !rJobSetup.mpData || (rJobSetup.mpData->mnRefCount < 0xFFFE), "JobSetup: RefCount overflow" );
161
162 mpData = rJobSetup.mpData;
163 if ( mpData )
164 mpData->mnRefCount++;
165 }
166
167 // -----------------------------------------------------------------------
168
~JobSetup()169 JobSetup::~JobSetup()
170 {
171 DBG_DTOR( JobSetup, NULL );
172
173 if ( mpData )
174 {
175 if ( mpData->mnRefCount == 1 )
176 delete mpData;
177 else
178 mpData->mnRefCount--;
179 }
180 }
181
182 // -----------------------------------------------------------------------
183
GetPrinterName() const184 XubString JobSetup::GetPrinterName() const
185 {
186 if ( mpData )
187 return mpData->maPrinterName;
188 else
189 {
190 XubString aName;
191 return aName;
192 }
193 }
194
195 // -----------------------------------------------------------------------
196
GetDriverName() const197 XubString JobSetup::GetDriverName() const
198 {
199 if ( mpData )
200 return mpData->maDriver;
201 else
202 {
203 XubString aDriver;
204 return aDriver;
205 }
206 }
207
208 // -----------------------------------------------------------------------
209
GetValue(const String & rKey) const210 String JobSetup::GetValue( const String& rKey ) const
211 {
212 if( mpData )
213 {
214 ::std::hash_map< ::rtl::OUString, ::rtl::OUString, ::rtl::OUStringHash >::const_iterator it;
215 it = mpData->maValueMap.find( rKey );
216 return it != mpData->maValueMap.end() ? String( it->second ) : String();
217 }
218 return String();
219 }
220
221 // -----------------------------------------------------------------------
222
SetValue(const String & rKey,const String & rValue)223 void JobSetup::SetValue( const String& rKey, const String& rValue )
224 {
225 if( ! mpData )
226 mpData = new ImplJobSetup();
227
228 mpData->maValueMap[ rKey ] = rValue;
229 }
230
231 // -----------------------------------------------------------------------
232
operator =(const JobSetup & rJobSetup)233 JobSetup& JobSetup::operator=( const JobSetup& rJobSetup )
234 {
235 DBG_CHKTHIS( JobSetup, NULL );
236 DBG_CHKOBJ( &rJobSetup, JobSetup, NULL );
237 DBG_ASSERT( !rJobSetup.mpData || (rJobSetup.mpData->mnRefCount) < 0xFFFE, "JobSetup: RefCount overflow" );
238
239 // Zuerst Referenzcounter erhoehen, damit man sich selbst zuweisen kann
240 if ( rJobSetup.mpData )
241 rJobSetup.mpData->mnRefCount++;
242
243 // Wenn es keine statischen ImpDaten sind, dann loeschen, wenn es
244 // die letzte Referenz ist, sonst Referenzcounter decrementieren
245 if ( mpData )
246 {
247 if ( mpData->mnRefCount == 1 )
248 delete mpData;
249 else
250 mpData->mnRefCount--;
251 }
252
253 mpData = rJobSetup.mpData;
254
255 return *this;
256 }
257
258 // -----------------------------------------------------------------------
259
operator ==(const JobSetup & rJobSetup) const260 sal_Bool JobSetup::operator==( const JobSetup& rJobSetup ) const
261 {
262 DBG_CHKTHIS( JobSetup, NULL );
263 DBG_CHKOBJ( &rJobSetup, JobSetup, NULL );
264
265 if ( mpData == rJobSetup.mpData )
266 return sal_True;
267
268 if ( !mpData || !rJobSetup.mpData )
269 return sal_False;
270
271 ImplJobSetup* pData1 = mpData;
272 ImplJobSetup* pData2 = rJobSetup.mpData;
273 if ( (pData1->mnSystem == pData2->mnSystem) &&
274 (pData1->maPrinterName == pData2->maPrinterName) &&
275 (pData1->maDriver == pData2->maDriver) &&
276 (pData1->meOrientation == pData2->meOrientation) &&
277 (pData1->meDuplexMode == pData2->meDuplexMode) &&
278 (pData1->mnPaperBin == pData2->mnPaperBin) &&
279 (pData1->mePaperFormat == pData2->mePaperFormat) &&
280 (pData1->mnPaperWidth == pData2->mnPaperWidth) &&
281 (pData1->mnPaperHeight == pData2->mnPaperHeight) &&
282 (pData1->mnDriverDataLen == pData2->mnDriverDataLen) &&
283 (memcmp( pData1->mpDriverData, pData2->mpDriverData, pData1->mnDriverDataLen ) == 0) &&
284 (pData1->maValueMap == pData2->maValueMap)
285 )
286 return sal_True;
287
288 return sal_False;
289 }
290
291 // -----------------------------------------------------------------------
292
operator >>(SvStream & rIStream,JobSetup & rJobSetup)293 SvStream& operator>>( SvStream& rIStream, JobSetup& rJobSetup )
294 {
295 DBG_ASSERTWARNING( rIStream.GetVersion(), "JobSetup::>> - Solar-Version not set on rOStream" );
296
297 // Zur Zeit haben wir noch kein neues FileFormat
298 // if ( rIStream.GetVersion() < JOBSET_FILEFORMAT2 )
299 {
300 sal_Size nFirstPos = rIStream.Tell();
301
302 sal_uInt16 nLen = 0;
303 rIStream >> nLen;
304
305 sal_uInt16 nSystem = 0;
306 if ( nLen < sizeof( nLen ) + sizeof( nSystem) )
307 return rIStream;
308 rIStream >> nSystem;
309
310 char* pTempBuf = new char[nLen];
311 rIStream.Read( pTempBuf, nLen - sizeof( nLen ) - sizeof( nSystem ) );
312 if ( nLen >= sizeof(ImplOldJobSetupData)+4 )
313 {
314 ImplOldJobSetupData* pData = (ImplOldJobSetupData*)pTempBuf;
315 if ( rJobSetup.mpData )
316 {
317 if ( rJobSetup.mpData->mnRefCount == 1 )
318 delete rJobSetup.mpData;
319 else
320 rJobSetup.mpData->mnRefCount--;
321 }
322
323 rtl_TextEncoding aStreamEncoding = RTL_TEXTENCODING_UTF8;
324 if( nSystem == JOBSET_FILE364_SYSTEM )
325 aStreamEncoding = rIStream.GetStreamCharSet();
326
327 rJobSetup.mpData = new ImplJobSetup;
328 ImplJobSetup* pJobData = rJobSetup.mpData;
329 pJobData->maPrinterName = UniString( pData->cPrinterName, aStreamEncoding );
330 pJobData->maDriver = UniString( pData->cDriverName, aStreamEncoding );
331
332 // Sind es unsere neuen JobSetup-Daten?
333 if ( nSystem == JOBSET_FILE364_SYSTEM ||
334 nSystem == JOBSET_FILE605_SYSTEM )
335 {
336 Impl364JobSetupData* pOldJobData = (Impl364JobSetupData*)(pTempBuf + sizeof( ImplOldJobSetupData ));
337 sal_uInt16 nOldJobDataSize = SVBT16ToShort( pOldJobData->nSize );
338 pJobData->mnSystem = SVBT16ToShort( pOldJobData->nSystem );
339 pJobData->mnDriverDataLen = SVBT32ToUInt32( pOldJobData->nDriverDataLen );
340 pJobData->meOrientation = (Orientation)SVBT16ToShort( pOldJobData->nOrientation );
341 pJobData->meDuplexMode = DUPLEX_UNKNOWN;
342 pJobData->mnPaperBin = SVBT16ToShort( pOldJobData->nPaperBin );
343 pJobData->mePaperFormat = (Paper)SVBT16ToShort( pOldJobData->nPaperFormat );
344 pJobData->mnPaperWidth = (long)SVBT32ToUInt32( pOldJobData->nPaperWidth );
345 pJobData->mnPaperHeight = (long)SVBT32ToUInt32( pOldJobData->nPaperHeight );
346 if ( pJobData->mnDriverDataLen )
347 {
348 sal_uInt8* pDriverData = ((sal_uInt8*)pOldJobData) + nOldJobDataSize;
349 pJobData->mpDriverData = (sal_uInt8*)rtl_allocateMemory( pJobData->mnDriverDataLen );
350 memcpy( pJobData->mpDriverData, pDriverData, pJobData->mnDriverDataLen );
351 }
352 if( nSystem == JOBSET_FILE605_SYSTEM )
353 {
354 rIStream.Seek( nFirstPos + sizeof( ImplOldJobSetupData ) + 4 + sizeof( Impl364JobSetupData ) + pJobData->mnDriverDataLen );
355 while( rIStream.Tell() < nFirstPos + nLen )
356 {
357 String aKey, aValue;
358 rIStream.ReadByteString( aKey, RTL_TEXTENCODING_UTF8 );
359 rIStream.ReadByteString( aValue, RTL_TEXTENCODING_UTF8 );
360 if( aKey.EqualsAscii( "COMPAT_DUPLEX_MODE" ) )
361 {
362 if( aValue.EqualsAscii( "DUPLEX_UNKNOWN" ) )
363 pJobData->meDuplexMode = DUPLEX_UNKNOWN;
364 else if( aValue.EqualsAscii( "DUPLEX_OFF" ) )
365 pJobData->meDuplexMode = DUPLEX_OFF;
366 else if( aValue.EqualsAscii( "DUPLEX_SHORTEDGE" ) )
367 pJobData->meDuplexMode = DUPLEX_SHORTEDGE;
368 else if( aValue.EqualsAscii( "DUPLEX_LONGEDGE" ) )
369 pJobData->meDuplexMode = DUPLEX_LONGEDGE;
370 }
371 else
372 pJobData->maValueMap[ aKey ] = aValue;
373 }
374 DBG_ASSERT( rIStream.Tell() == nFirstPos+nLen, "corrupted job setup" );
375 // ensure correct stream position
376 rIStream.Seek( nFirstPos + nLen );
377 }
378 }
379 }
380 delete[] pTempBuf;
381 }
382 /*
383 else
384 {
385 }
386 */
387
388 return rIStream;
389 }
390
391 // -----------------------------------------------------------------------
392
operator <<(SvStream & rOStream,const JobSetup & rJobSetup)393 SvStream& operator<<( SvStream& rOStream, const JobSetup& rJobSetup )
394 {
395 DBG_ASSERTWARNING( rOStream.GetVersion(), "JobSetup::<< - Solar-Version not set on rOStream" );
396
397 // Zur Zeit haben wir noch kein neues FileFormat
398 // if ( rOStream.GetVersion() < JOBSET_FILEFORMAT2 )
399 {
400 sal_uInt16 nLen = 0;
401 if ( !rJobSetup.mpData )
402 rOStream << nLen;
403 else
404 {
405 sal_uInt16 nSystem = JOBSET_FILE605_SYSTEM;
406
407 const ImplJobSetup* pJobData = rJobSetup.ImplGetConstData();
408 Impl364JobSetupData aOldJobData;
409 sal_uInt16 nOldJobDataSize = sizeof( aOldJobData );
410 ShortToSVBT16( nOldJobDataSize, aOldJobData.nSize );
411 ShortToSVBT16( pJobData->mnSystem, aOldJobData.nSystem );
412 UInt32ToSVBT32( pJobData->mnDriverDataLen, aOldJobData.nDriverDataLen );
413 ShortToSVBT16( (sal_uInt16)(pJobData->meOrientation), aOldJobData.nOrientation );
414 ShortToSVBT16( pJobData->mnPaperBin, aOldJobData.nPaperBin );
415 ShortToSVBT16( (sal_uInt16)(pJobData->mePaperFormat), aOldJobData.nPaperFormat );
416 UInt32ToSVBT32( (sal_uLong)(pJobData->mnPaperWidth), aOldJobData.nPaperWidth );
417 UInt32ToSVBT32( (sal_uLong)(pJobData->mnPaperHeight), aOldJobData.nPaperHeight );
418
419 ImplOldJobSetupData aOldData;
420 memset( &aOldData, 0, sizeof( aOldData ) );
421 ByteString aPrnByteName( rJobSetup.GetPrinterName(), RTL_TEXTENCODING_UTF8 );
422 strncpy( aOldData.cPrinterName, aPrnByteName.GetBuffer(), 63 );
423 ByteString aDriverByteName( rJobSetup.GetDriverName(), RTL_TEXTENCODING_UTF8 );
424 strncpy( aOldData.cDriverName, aDriverByteName.GetBuffer(), 31 );
425 // nLen = sizeof( aOldData ) + 4 + nOldJobDataSize + pJobData->mnDriverDataLen;
426 int nPos = rOStream.Tell();
427 rOStream << nLen;
428 rOStream << nSystem;
429 rOStream.Write( (char*)&aOldData, sizeof( aOldData ) );
430 rOStream.Write( (char*)&aOldJobData, nOldJobDataSize );
431 rOStream.Write( (char*)pJobData->mpDriverData, pJobData->mnDriverDataLen );
432 ::std::hash_map< ::rtl::OUString, ::rtl::OUString, ::rtl::OUStringHash >::const_iterator it;
433 for( it = pJobData->maValueMap.begin(); it != pJobData->maValueMap.end(); ++it )
434 {
435 rOStream.WriteByteString( it->first, RTL_TEXTENCODING_UTF8 );
436 rOStream.WriteByteString( it->second, RTL_TEXTENCODING_UTF8 );
437 }
438 rOStream.WriteByteString( "COMPAT_DUPLEX_MODE" ) ;
439 switch( pJobData->meDuplexMode )
440 {
441 case DUPLEX_UNKNOWN: rOStream.WriteByteString( "DUPLEX_UNKNOWN" );break;
442 case DUPLEX_OFF: rOStream.WriteByteString( "DUPLEX_OFF" );break;
443 case DUPLEX_SHORTEDGE: rOStream.WriteByteString( "DUPLEX_SHORTEDGE" );break;
444 case DUPLEX_LONGEDGE: rOStream.WriteByteString( "DUPLEX_LONGEDGE" );break;
445 }
446 nLen = sal::static_int_cast<sal_uInt16>(rOStream.Tell() - nPos);
447 rOStream.Seek( nPos );
448 rOStream << nLen;
449 rOStream.Seek( nPos + nLen );
450 }
451 }
452 /*
453 else
454 {
455 }
456 */
457
458 return rOStream;
459 }
460