Subversion Repositories DevTools

Rev

Rev 2265 | Go to most recent revision | Details | Last modification | View Log | RSS feed

Rev Author Line No. Line
2263 kivins 1
//## begin module%1.7%.codegen_version preserve=yes
2
//   Read the documentation to learn more about C++ code generator
3
//   versioning.
4
//## end module%1.7%.codegen_version
5
 
6
//## begin module%41F607FA0261.cm preserve=no
7
//## end module%41F607FA0261.cm
8
 
9
//## begin module%41F607FA0261.cp preserve=no
10
//	C O P Y R I G H T   N O T I C E
11
//	This material is confidential to ERG and may not be disclosed in whole
12
//	or in part to any third party nor used in any manner whatsoever other
13
//	than for the purposes expressly consented to by ERG in writing.
14
//
15
//	This material is also copyright and may not be reproduced, stored in a
16
//	retrieval system or transmitted in any form or by any means in whole or
17
//	in part without the express written consent of ERG.
18
//## end module%41F607FA0261.cp
19
 
20
//## Module: TransactionSpecification%41F607FA0261; Pseudo Package body
21
//## Subsystem: MASS::Dev::Tools::TxnTestManager::src%41F5A79001E4
22
//## Source file: Z:\MASS_Dev\Tools\TxnTestManager\src\TransactionSpecification.cpp
23
 
24
//## begin module%41F607FA0261.additionalIncludes preserve=no
25
//## end module%41F607FA0261.additionalIncludes
26
 
27
//## begin module%41F607FA0261.includes preserve=yes
28
#pragma warn -com
29
#include <LoggingMacros.h>
30
#pragma warn +com
31
//## end module%41F607FA0261.includes
32
 
33
// IXmlSchemaWrapperSchema
34
#include "IXmlSchemaWrapperSchema.h"
35
// IXmlSchemaWrapperString
36
#include "IXmlSchemaWrapperString.h"
37
// Iteration
38
#include "Iteration.h"
39
// TestScenario
40
#include "TestScenario.h"
41
// TimeEstimate
42
#include "TimeEstimate.h"
43
// ProgressBar
44
#include "ProgressBar.h"
45
// IXmlSchemaWrapperByteArray
46
#include "IXmlSchemaWrapperByteArray.h"
47
// IXmlSchemaWrapperElement
48
#include "IXmlSchemaWrapperElement.h"
49
// IXmlSchemaWrapperFactory
50
#include "IXmlSchemaWrapperFactory.h"
51
// IXmlSchemaWrapperStream
52
#include "IXmlSchemaWrapperStream.h"
53
// TransactionSpecificationValue
54
#include "TransactionSpecificationValue.h"
55
// TransactionSpecification
56
#include "TransactionSpecification.h"
57
// MacQualification
58
#include "MacQualification.h"
59
// EvaluationCallback
60
#include "EvaluationCallback.h"
61
// EvaluationContext
62
#include "EvaluationContext.h"
63
// TransactionStream
64
#include "TransactionStream.h"
65
// TransactionStructure
66
#include "TransactionStructure.h"
67
// IHash
68
#include "IHash.h"
69
// IMessageDigest
70
#include "IMessageDigest.h"
71
//## begin module%41F607FA0261.additionalDeclarations preserve=yes
72
#include <sstream>
73
#include "Utilities.h"
74
 
75
#define COMPENSATE_FOR_PARSER_BUG 0
76
#if COMPENSATE_FOR_PARSER_BUG
77
static void rotateBuffer( unsigned char * buffer, const unsigned int & length )
78
{
79
	unsigned char b;
80
 
81
	for ( unsigned int i=0, j=length-1; i<length/2; ++i,--j )
82
	{
83
		b = buffer[ i ];
84
		buffer[ i ] = buffer[ j ];
85
		buffer[ j ] = b;
86
	}
87
}
88
#endif
89
 
90
//## end module%41F607FA0261.additionalDeclarations
91
 
92
 
93
// Class TransactionSpecification 
94
 
95
//## begin TransactionSpecification::headerStructureName%4206D764033E.attr preserve=no  private: static char {RAC} "SysHdr_t"
96
const char *TransactionSpecification::g_headerStructureName = "SysHdr_t";
97
//## end TransactionSpecification::headerStructureName%4206D764033E.attr
98
 
99
//## Operation: TransactionSpecification%41F7060D0204
100
TransactionSpecification::TransactionSpecification (const int &transactionSpecificationNumber)
101
  //## begin TransactionSpecification::TransactionSpecification%41F7060D0204.hasinit preserve=no
102
      : m_structureIndex(0),
103
        m_transactionSpecificationNumber(0),
104
        m_udSubtype(0),
105
        m_udType(0),
106
        m_formatVersion(0),
107
        m_scenario(0),
108
        m_string(0),
109
        m_structure(0),
110
        m_macFields(0)
111
  //## end TransactionSpecification::TransactionSpecification%41F7060D0204.hasinit
112
  //## begin TransactionSpecification::TransactionSpecification%41F7060D0204.initialization preserve=yes
113
  //## end TransactionSpecification::TransactionSpecification%41F7060D0204.initialization
114
{
115
  //## begin TransactionSpecification::TransactionSpecification%41F7060D0204.body preserve=yes
116
 
117
  m_transactionSpecificationNumber = transactionSpecificationNumber;
118
 
119
  //## end TransactionSpecification::TransactionSpecification%41F7060D0204.body
120
}
121
 
122
//## Operation: TransactionSpecification%42045473030D
123
TransactionSpecification::TransactionSpecification (const int &transactionSpecificationNumber, const std::string &payloadStructureName, TestScenario& scenario)
124
  //## begin TransactionSpecification::TransactionSpecification%42045473030D.hasinit preserve=no
125
      : m_structureIndex(0),
126
        m_transactionSpecificationNumber(0),
127
        m_udSubtype(0),
128
        m_udType(0),
129
        m_formatVersion(0),
130
        m_scenario(0),
131
        m_string(0),
132
        m_structure(0),
133
        m_macFields(0)
134
  //## end TransactionSpecification::TransactionSpecification%42045473030D.hasinit
135
  //## begin TransactionSpecification::TransactionSpecification%42045473030D.initialization preserve=yes
136
  //## end TransactionSpecification::TransactionSpecification%42045473030D.initialization
137
{
138
  //## begin TransactionSpecification::TransactionSpecification%42045473030D.body preserve=yes
139
 
140
	m_formatVersion	= scenario.getIteration().getFormatVersion();
141
	m_scenario		= &scenario;
142
	m_string
143
		= &scenario.getIteration().getSchemaWrapperFactory().createString();
144
	m_structureName	= payloadStructureName;
145
	m_transactionSpecificationNumber
146
		= transactionSpecificationNumber;
147
 
148
	// Allocate the structures that we'll need for this transaction.
149
	TransactionStructure * object = 0;
150
	try
151
	{
152
		object =new TransactionStructure(
153
			g_headerStructureName,
154
			m_scenario->getIteration().getIterationId(),
155
			m_scenario->getIteration().getSchemaWrapperFactory(),
156
			m_scenario->getIteration().getSchema(),
157
			true );
158
		m_structure.push_back( object );
159
		object = 0;
160
 
161
		object =new TransactionStructure(
162
			payloadStructureName,
163
			m_scenario->getIteration().getIterationId(),
164
			m_scenario->getIteration().getSchemaWrapperFactory(),
165
			m_scenario->getIteration().getSchema(),
166
			false );
167
		m_structure.push_back( object );
168
		object = 0;
169
	}
170
	catch ( ... )
171
	{
172
		// Rollback.
173
		delete object;
174
		object = 0;
175
 
176
		for ( std::vector< TransactionStructure * >::iterator
177
				structure = m_structure.begin();
178
			  structure != m_structure.end();
179
			  ++structure )
180
		{
181
			delete *structure;
182
			*structure = 0;
183
		}
184
		m_structure.clear();
185
 
186
		throw;
187
	}
188
 
189
  //## end TransactionSpecification::TransactionSpecification%42045473030D.body
190
}
191
 
192
 
193
TransactionSpecification::~TransactionSpecification()
194
{
195
  //## begin TransactionSpecification::~TransactionSpecification%41F607FA0261_dest.body preserve=yes
196
 
197
	for ( std::map< std::string, TransactionSpecificationValue * >::iterator
198
			transaction = m_value.begin();
199
		  transaction != m_value.end();
200
		  ++transaction )
201
	{
202
		delete transaction->second;
203
		transaction->second = 0;
204
	}
205
	m_value.clear();
206
 
207
	for ( std::vector< TransactionStructure * >::iterator
208
			structure = m_structure.begin();
209
		  structure != m_structure.end();
210
		  ++structure )
211
	{
212
		delete *structure;
213
		*structure = 0;
214
	}
215
	m_structure.clear();
216
 
217
	if ( m_string && m_scenario )
218
	{
219
		m_scenario->getIteration().getSchemaWrapperFactory().destroyString( *m_string );
220
		m_string = 0;
221
	}
222
	m_scenario = 0;	// We don't own this object.
223
 
224
  //## end TransactionSpecification::~TransactionSpecification%41F607FA0261_dest.body
225
}
226
 
227
 
228
 
229
//## Other Operations (implementation)
230
//## Operation: addMacField%4212DBC1031E
231
void TransactionSpecification::addMacField (XMLSchema::IXmlSchemaWrapperElement &element)
232
{
233
  //## begin TransactionSpecification::addMacField%4212DBC1031E.body preserve=yes
234
 
235
	m_macFields.push_back( &element );  
236
 
237
  //## end TransactionSpecification::addMacField%4212DBC1031E.body
238
}
239
 
240
//## Operation: addValue%41F70652035C
241
void TransactionSpecification::addValue (const std::string &xPath, const std::string &value, const bool &obsolete)
242
{
243
  //## begin TransactionSpecification::addValue%41F70652035C.body preserve=yes
244
 
245
	TransactionSpecificationValue * theValue = 0;
246
 
247
	try
248
	{
249
		theValue = new TransactionSpecificationValue( xPath, value, obsolete );
250
 
251
		if ( !m_value.insert(
252
				std::map< std::string, TransactionSpecificationValue * >::value_type(
253
					theValue->getXPath(),
254
					theValue ) ).second )
255
		{
256
			MTHROW( std::runtime_error, \
257
				"Cannot add value \"" \
258
				<< theValue->getXPath() \
259
				<< "\" to transaction " \
260
				<< m_transactionSpecificationNumber \
261
				<< '.' );
262
		}
263
	}
264
	catch ( ... )
265
	{
266
		delete theValue;
267
		theValue = 0;
268
 
269
		throw;
270
	}
271
 
272
  //## end TransactionSpecification::addValue%41F70652035C.body
273
}
274
 
275
//## Operation: clearMacFields%42130B2D0377
276
void TransactionSpecification::clearMacFields ()
277
{
278
  //## begin TransactionSpecification::clearMacFields%42130B2D0377.body preserve=yes
279
 
280
	XMLSchema::IXmlSchemaWrapperFactory & factory
281
		= m_scenario->getIteration().getSchemaWrapperFactory();
282
	for ( std::vector< XMLSchema::IXmlSchemaWrapperElement * >
283
			::iterator element = m_macFields.begin();
284
		  element != m_macFields.end();
285
		  ++element )
286
	{
287
		factory.destroySchemaElement( **element );
288
		*element = 0;
289
	}
290
	m_macFields.clear();
291
 
292
  //## end TransactionSpecification::clearMacFields%42130B2D0377.body
293
}
294
 
295
//## Operation: clearMarks%41F705790276
296
void TransactionSpecification::clearMarks ()
297
{
298
  //## begin TransactionSpecification::clearMarks%41F705790276.body preserve=yes
299
 
300
	for ( std::map< std::string, TransactionSpecificationValue * >::iterator
301
			where = m_value.begin();
302
		  where != m_value.end();
303
		  ++where )
304
	{
305
		where->second->unmark();
306
	}
307
 
308
  //## end TransactionSpecification::clearMarks%41F705790276.body
309
}
310
 
311
//## Operation: generate%4204564D02F3
312
const bool TransactionSpecification::generate (TransactionStream& stream, const bool &generateHeaders, EvaluationContext& evaluationContext)
313
{
314
  //## begin TransactionSpecification::generate%4204564D02F3.body preserve=yes
315
 
316
	XMLSchema::IXmlSchemaWrapperFactory & xmlSchemaWrapperFactory
317
		= m_scenario->getIteration().getSchemaWrapperFactory();
318
 
319
	/**
320
	 *	Traverse the structures associated with this transaction  in order,
321
	 *	querying our collection of defined fields for every schema element
322
	 *	that we encounter.  When we have a match, then we evaluate the
323
	 *	expression found, and assign the result to the schema element currently
324
	 * 	being visited.
325
	 */
326
 
327
	evaluationContext.setTransaction( *this );
328
 
329
	EvaluationCallback callback( *this, evaluationContext );
330
 
331
	bool generated = false;
332
	m_structureIndex = 0;
333
	std::vector< TransactionStructure * >::iterator structure;
334
	for ( structure = m_structure.begin();
335
		  structure != m_structure.end();
336
		  ++structure )
337
	{
338
		if ( generateHeaders || !(*structure)->isHeader() )
339
		{
340
			generated = (*structure)->getSchemaElement().traverse( callback );
341
			if ( !generated )
342
			{
343
				break;
344
			}
345
		}
346
		++m_structureIndex;
347
	}
348
 
349
	if ( generated )
350
	{
351
		/**
352
		 *	If we have any MAC fields, then we must compute the MAC and assign
353
		 *	the MAC to each element in the collection.
354
		 */
355
		if ( m_macFields.size() )
356
		{
357
			if ( evaluationContext.haveMessageDigest() )
358
			{
359
				/**
360
				 *	Create a serialsation stream, and serialise all attributes
361
				 *	into it that are to be included in the MAC.  Then MAC the
362
				 *	stream.  We need to do this because we need to MAC the
363
				 *	serialised form, not the internal binary form.
364
				 */
365
				MacQualification macQualification( evaluationContext );
366
 
367
				XMLSchema::IXmlSchemaWrapperStream *	stream	= 0;
368
				XMLSchema::IXmlSchemaWrapperByteArray *	digest	= 0;
369
 
370
				try
371
				{
372
					stream = &xmlSchemaWrapperFactory.createXdrStream();
373
					digest = &xmlSchemaWrapperFactory.createByteArray();
374
 
375
					for ( structure = m_structure.begin();
376
						  structure != m_structure.end();
377
						  ++structure )
378
					{
379
						// We only include the structure in the MAC computation,
380
						// never the header.
381
						if ( !(*structure)->isHeader() )
382
						{
383
							if ( !(*structure)->write(
384
									*stream,
385
									macQualification ) )
386
							{
387
								generated = false;
388
								break;
389
							}
390
						}
391
					}
392
 
393
					if ( generated )
394
					{
395
						void *			buffer = 0;
396
						unsigned int	length = 0;
397
 
398
						// When we get a zero-length MAC, we don't assign it.
399
						if ( stream->getData( buffer, length ) )
400
						{
401
							evaluationContext.getMessageDigest().reset();
402
 
403
							if ( evaluationContext.haveHash() )
404
							{
405
								IHash & hash = evaluationContext.getHash();
406
 
407
								hash.reset();
408
								generated =
409
									hash.updateByteArray(
410
										buffer,
411
										length ) &&
412
									hash.digest();
413
								if ( generated )
414
								{
415
									generated = evaluationContext.
416
										getMessageDigest().updateByteArray(
417
											hash.getValue(),
418
											hash.getLength() );
419
								}
420
							}
421
							else
422
							{
423
								generated = evaluationContext.getMessageDigest().
424
									updateByteArray( buffer, length );
425
							}
426
							if ( generated )
427
							{
428
								if ( evaluationContext.getMessageDigest().digest() )
429
								{
430
									if ( evaluationContext.getMessageDigest().getLength() )
431
									{
432
#if COMPENSATE_FOR_PARSER_BUG
433
										/**
434
										 *	Compensate for the parser treating
435
										 *	an array of 8 U8 as a U64 (Why does
436
										 *	it do that?  Its wrong.).
437
										 */
438
										unsigned char * b = const_cast< unsigned char * >( evaluationContext.getMessageDigest().getValue() );
439
										length = evaluationContext.getMessageDigest().getLength();
440
										rotateBuffer( b, length );
441
										digest->assign( b, length );
442
#else
443
										digest->assign(
444
											evaluationContext.getMessageDigest().getValue(),
445
											evaluationContext.getMessageDigest().getLength() );
446
#endif // #ifdef COMPENSATE_FOR_PARSER_BUG
447
 
448
										for ( std::vector< XMLSchema::IXmlSchemaWrapperElement * >
449
												::iterator macField = m_macFields.begin();
450
											  macField != m_macFields.end();
451
											  ++macField )
452
										{
453
											if ( !(*macField)->setByteArray( *digest ) )
454
											{
455
												generated = false;
456
												break;
457
											}
458
										}
459
									}
460
									else
461
									{
462
										generated = false;
463
									}
464
								}
465
								else
466
								{
467
									generated = false;
468
								}
469
							}
470
						}
471
					}
472
 
473
				}
474
				__finally
475
				{
476
					if ( digest )
477
					{
478
						xmlSchemaWrapperFactory.destroyByteArray( *digest );
479
						digest = 0;
480
					}
481
 
482
					if ( stream )
483
					{
484
						xmlSchemaWrapperFactory.destroyStream( *stream );
485
						stream = 0;
486
					}
487
				}
488
			}
489
			else
490
			{
491
				generated = false;
492
			}
493
 
494
			if ( !generated )
495
			{
496
				std::stringstream message;
497
				message
498
					<< "Cannot compute MAC.  Is the security subsystem operational?";
499
				MERROR( message.str() );
500
				message << "  Ignore the error and continue?";
501
 
502
				generated = ( MessageDlg(
503
									message.str().c_str(),
504
									mtConfirmation,
505
									TMsgDlgButtons() << mbYes << mbNo,
506
 
507
			}
508
			clearMacFields();
509
		}
510
	}
511
 
512
	if ( generated )
513
	{
514
		for ( structure = m_structure.begin();
515
			  structure != m_structure.end();
516
			  ++structure )
517
		{
518
			if ( generateHeaders || !(*structure)->isHeader() )
519
			{
520
				/**
521
				 *	Serialise the structure into the transaction stream.
522
				 */
523
				generated = (*structure)->write( stream );
524
				if ( !generated )
525
				{
526
					break;
527
				}
528
			}
529
		}
530
 
531
		stream.incrementCount();
532
		if ( evaluationContext.haveProgressBar() )
533
		{
534
			evaluationContext.getProgressBar().increment();
535
		}
536
		evaluationContext.getTimeEstimate().increment();
537
	}
538
 
539
	return ( generated );
540
 
541
  //## end TransactionSpecification::generate%4204564D02F3.body
542
}
543
 
544
//## Operation: getCurrentStructure%4213183F01DD
545
const TransactionStructure & TransactionSpecification::getCurrentStructure () const
546
{
547
  //## begin TransactionSpecification::getCurrentStructure%4213183F01DD.body preserve=yes
548
 
549
	return ( *m_structure[ m_structureIndex ] );  
550
 
551
  //## end TransactionSpecification::getCurrentStructure%4213183F01DD.body
552
}
553
 
554
//## Operation: getFormatVersion%4208BB80011D
555
const int & TransactionSpecification::getFormatVersion () const
556
{
557
  //## begin TransactionSpecification::getFormatVersion%4208BB80011D.body preserve=yes
558
 
559
	return ( m_formatVersion );
560
 
561
  //## end TransactionSpecification::getFormatVersion%4208BB80011D.body
562
}
563
 
564
//## Operation: getScenario%420471B00192
565
const TestScenario & TransactionSpecification::getScenario () const
566
{
567
  //## begin TransactionSpecification::getScenario%420471B00192.body preserve=yes
568
 
569
	return ( *m_scenario );
570
 
571
  //## end TransactionSpecification::getScenario%420471B00192.body
572
}
573
 
574
//## Operation: getTransactionField%4204283B033E
575
TransactionSpecificationValue& TransactionSpecification::getTransactionField (const std::string &xpath)
576
{
577
  //## begin TransactionSpecification::getTransactionField%4204283B033E.body preserve=yes
578
 
579
	std::map< std::string, TransactionSpecificationValue * >::const_iterator
580
		instance = m_value.find( xpath );
581
 
582
	if ( instance != m_value.end() )
583
	{
584
		return ( *instance->second );
585
	}
586
	else
587
	{
588
		TransactionSpecificationValue * object = 0;
589
 
590
		try
591
		{
592
			object = new TransactionSpecificationValue( xpath, *this );
593
 
594
			if ( m_value.insert(
595
					std::map< std::string, TransactionSpecificationValue * >::value_type(
596
						xpath,
597
						object ) ).second )
598
			{
599
				return ( *object );
600
			}
601
			else
602
			{
603
				MTHROW( std::runtime_error, \
604
					"Cannot add transaction field \"" \
605
					<< xpath \
606
					<< "\" to transaction " \
607
					<< m_transactionSpecificationNumber \
608
					<< '.' );
609
			}
610
		}
611
		catch ( ... )
612
		{
613
			delete object;
614
			object = 0;
615
 
616
			throw;
617
		}
618
	}
619
 
620
  //## end TransactionSpecification::getTransactionField%4204283B033E.body
621
}
622
 
623
//## Operation: getTransactionSpecificationNumber%41F71AD2002F
624
const int & TransactionSpecification::getTransactionSpecificationNumber () const
625
{
626
  //## begin TransactionSpecification::getTransactionSpecificationNumber%41F71AD2002F.body preserve=yes
627
 
628
	return ( m_transactionSpecificationNumber );
629
 
630
  //## end TransactionSpecification::getTransactionSpecificationNumber%41F71AD2002F.body
631
}
632
 
633
//## Operation: getUdSubtype%4208AFAF01F7
634
const unsigned short & TransactionSpecification::getUdSubtype () const
635
{
636
  //## begin TransactionSpecification::getUdSubtype%4208AFAF01F7.body preserve=yes
637
 
638
	return ( m_udSubtype );
639
 
640
  //## end TransactionSpecification::getUdSubtype%4208AFAF01F7.body
641
}
642
 
643
//## Operation: getUdType%4208AFAF0245
644
const unsigned short & TransactionSpecification::getUdType () const
645
{
646
  //## begin TransactionSpecification::getUdType%4208AFAF0245.body preserve=yes
647
 
648
	return ( m_udType );
649
 
650
  //## end TransactionSpecification::getUdType%4208AFAF0245.body
651
}
652
 
653
//## Operation: getValues%41F705A600AC
654
const std::map< std::string, TransactionSpecificationValue * > & TransactionSpecification::getValues () const
655
{
656
  //## begin TransactionSpecification::getValues%41F705A600AC.body preserve=yes
657
 
658
	return ( m_value );
659
 
660
  //## end TransactionSpecification::getValues%41F705A600AC.body
661
}
662
 
663
//## Operation: isContained%41F70575014E
664
const bool TransactionSpecification::isContained (const std::string &xPath) const
665
{
666
  //## begin TransactionSpecification::isContained%41F70575014E.body preserve=yes
667
 
668
  return ( m_value.find( xPath ) != m_value.end() );
669
 
670
  //## end TransactionSpecification::isContained%41F70575014E.body
671
}
672
 
673
//## Operation: isMarked%41F708CB0307
674
const bool TransactionSpecification::isMarked (const std::string &xPath) const
675
{
676
  //## begin TransactionSpecification::isMarked%41F708CB0307.body preserve=yes
677
 
678
	std::map< std::string, TransactionSpecificationValue * >::const_iterator
679
		instance = m_value.find( xPath );
680
 
681
	if ( instance != m_value.end() )
682
	{
683
		return ( instance->second->isMarked() );
684
	}
685
	else
686
	{
687
		MTHROW( std::runtime_error, \
688
			"Cannot find value " << xPath << '.' );
689
	}
690
 
691
  //## end TransactionSpecification::isMarked%41F708CB0307.body
692
}
693
 
694
//## Operation: markValue%41F7069E002F
695
void TransactionSpecification::markValue (const std::string &xPath)
696
{
697
  //## begin TransactionSpecification::markValue%41F7069E002F.body preserve=yes
698
 
699
	std::map< std::string, TransactionSpecificationValue * >::const_iterator
700
		instance = m_value.find( xPath );
701
 
702
	if ( instance != m_value.end() )
703
	{
704
		instance->second->mark();
705
	}
706
	else
707
	{
708
		MTHROW( std::runtime_error, \
709
			"Cannot find value " << xPath << '.' );
710
	}
711
 
712
  //## end TransactionSpecification::markValue%41F7069E002F.body
713
}
714
 
715
//## Operation: setUdSubtype%42044110019A
716
const unsigned short & TransactionSpecification::setUdSubtype (const unsigned short &value)
717
{
718
  //## begin TransactionSpecification::setUdSubtype%42044110019A.body preserve=yes
719
 
720
	return ( m_udSubtype = value );
721
 
722
  //## end TransactionSpecification::setUdSubtype%42044110019A.body
723
}
724
 
725
//## Operation: setUdType%420440DE038E
726
const unsigned short & TransactionSpecification::setUdType (const unsigned short &value)
727
{
728
  //## begin TransactionSpecification::setUdType%420440DE038E.body preserve=yes
729
 
730
	return ( m_udType = value );
731
 
732
  //## end TransactionSpecification::setUdType%420440DE038E.body
733
}
734
 
735
//## Operation: evaluate%4205C6F500FC
736
const bool TransactionSpecification::evaluate (XMLSchema::IXmlSchemaWrapperElement &element, EvaluationContext& context)
737
{
738
  //## begin TransactionSpecification::evaluate%4205C6F500FC.body preserve=yes
739
 
740
	/**
741
	 *	Build an XPath from the name of the structure that we are traversing
742
	 *	right now and the xpath reported by the element being visited.  Then
743
	 *	look for a field with that XPath.
744
	 */
745
 
746
	std::stringstream xpath;
747
	if ( element.getAttributeValue( "xpath", *m_string ) )
748
	{
749
		xpath
750
			<< '/'
751
			<< m_structure[ m_structureIndex ]->getName()
752
			<< m_string->c_str();
753
 
754
		/**
755
		 *	Find the element if we have it.  We get calls for everything, not
756
		 *	just for what we have.  When we don't have the element, then we
757
		 *	have nothing to set, which is fine.
758
		 */
759
		std::map< std::string, TransactionSpecificationValue * >::iterator
760
			field = m_value.find( xpath.str() );
761
		if ( field != m_value.end() )
762
		{
763
			std::string value;
764
			bool postponed = false;
765
			if ( field->second->evaluate( value, true, context, postponed ) )
766
			{
767
				if ( !postponed )
768
				{
769
					*m_string = value.c_str();
770
					if ( element.setString( *m_string ) )
771
					{
772
						return ( true );
773
					}
774
					else
775
					{
776
						std::string datatype;
777
						if ( element.getAttributeValue( "datatype", *m_string ) )
778
						{
779
							datatype = m_string->c_str();
780
						}
781
 
782
						std::stringstream message;
783
						message
784
							<< "Cannot set value of \""
785
							<< xpath.str()
786
							<< "\" to \""
787
							<< value
788
							<< "\" as \""
789
							<< datatype
790
							<< "\".";
791
						MERROR( message.str() );
792
						message << "  Continue?";
793
 
794
						return ( MessageDlg(
795
									message.str().c_str(),
796
									mtConfirmation,
797
									TMsgDlgButtons() << mbYes << mbNo,
798
 
799
					}
800
				}
801
				else
802
				{
803
					return ( true );
804
				}
805
			}
806
			else
807
			{
808
				std::stringstream message;
809
				message
810
					<< "Cannot evaluate value of \"" \
811
					<< field->second->getExpression() \
812
					<< "\" for \"" \
813
					<< xpath.str() \
814
					<< "\".";
815
				MERROR( message.str() );
816
				message << "  Continue?";
817
 
818
				return ( MessageDlg(
819
							message.str().c_str(),
820
							mtConfirmation,
821
							TMsgDlgButtons() << mbYes << mbNo,
822
 
823
			}
824
		}
825
		else
826
		{
827
			// We have no value for this element, which is fine.
828
			return ( true );
829
		}
830
	}
831
	else
832
	{
833
		MERROR( "Cannot get xpath for schema element " << &element << '.' );
834
	}
835
 
836
	return ( false );
837
 
838
  //## end TransactionSpecification::evaluate%4205C6F500FC.body
839
}
840
 
841
// Additional Declarations
842
  //## begin TransactionSpecification%41F607FA0261.declarations preserve=yes
843
  //## end TransactionSpecification%41F607FA0261.declarations
844
 
845
//## begin module%41F607FA0261.epilog preserve=yes
846
//## end module%41F607FA0261.epilog