Subversion Repositories DevTools

Rev

Rev 2263 | Go to most recent revision | Details | Compare with Previous | 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
	{
2265 kivins 514
		stream.incrementCount();
515
 		for ( structure = m_structure.begin();
2263 kivins 516
			  structure != m_structure.end();
517
			  ++structure )
518
		{
519
			if ( generateHeaders || !(*structure)->isHeader() )
520
			{
521
				/**
522
				 *	Serialise the structure into the transaction stream.
523
				 */
524
				generated = (*structure)->write( stream );
525
				if ( !generated )
526
				{
527
					break;
528
				}
529
			}
530
		}
531
 
2265 kivins 532
 
2263 kivins 533
		if ( evaluationContext.haveProgressBar() )
534
		{
535
			evaluationContext.getProgressBar().increment();
536
		}
537
		evaluationContext.getTimeEstimate().increment();
538
	}
539
 
540
	return ( generated );
541
 
542
  //## end TransactionSpecification::generate%4204564D02F3.body
543
}
544
 
545
//## Operation: getCurrentStructure%4213183F01DD
546
const TransactionStructure & TransactionSpecification::getCurrentStructure () const
547
{
548
  //## begin TransactionSpecification::getCurrentStructure%4213183F01DD.body preserve=yes
549
 
550
	return ( *m_structure[ m_structureIndex ] );  
551
 
552
  //## end TransactionSpecification::getCurrentStructure%4213183F01DD.body
553
}
554
 
555
//## Operation: getFormatVersion%4208BB80011D
556
const int & TransactionSpecification::getFormatVersion () const
557
{
558
  //## begin TransactionSpecification::getFormatVersion%4208BB80011D.body preserve=yes
559
 
560
	return ( m_formatVersion );
561
 
562
  //## end TransactionSpecification::getFormatVersion%4208BB80011D.body
563
}
564
 
565
//## Operation: getScenario%420471B00192
566
const TestScenario & TransactionSpecification::getScenario () const
567
{
568
  //## begin TransactionSpecification::getScenario%420471B00192.body preserve=yes
569
 
570
	return ( *m_scenario );
571
 
572
  //## end TransactionSpecification::getScenario%420471B00192.body
573
}
574
 
575
//## Operation: getTransactionField%4204283B033E
576
TransactionSpecificationValue& TransactionSpecification::getTransactionField (const std::string &xpath)
577
{
578
  //## begin TransactionSpecification::getTransactionField%4204283B033E.body preserve=yes
579
 
580
	std::map< std::string, TransactionSpecificationValue * >::const_iterator
581
		instance = m_value.find( xpath );
582
 
583
	if ( instance != m_value.end() )
584
	{
585
		return ( *instance->second );
586
	}
587
	else
588
	{
589
		TransactionSpecificationValue * object = 0;
590
 
591
		try
592
		{
593
			object = new TransactionSpecificationValue( xpath, *this );
594
 
595
			if ( m_value.insert(
596
					std::map< std::string, TransactionSpecificationValue * >::value_type(
597
						xpath,
598
						object ) ).second )
599
			{
600
				return ( *object );
601
			}
602
			else
603
			{
604
				MTHROW( std::runtime_error, \
605
					"Cannot add transaction field \"" \
606
					<< xpath \
607
					<< "\" to transaction " \
608
					<< m_transactionSpecificationNumber \
609
					<< '.' );
610
			}
611
		}
612
		catch ( ... )
613
		{
614
			delete object;
615
			object = 0;
616
 
617
			throw;
618
		}
619
	}
620
 
621
  //## end TransactionSpecification::getTransactionField%4204283B033E.body
622
}
623
 
624
//## Operation: getTransactionSpecificationNumber%41F71AD2002F
625
const int & TransactionSpecification::getTransactionSpecificationNumber () const
626
{
627
  //## begin TransactionSpecification::getTransactionSpecificationNumber%41F71AD2002F.body preserve=yes
628
 
629
	return ( m_transactionSpecificationNumber );
630
 
631
  //## end TransactionSpecification::getTransactionSpecificationNumber%41F71AD2002F.body
632
}
633
 
634
//## Operation: getUdSubtype%4208AFAF01F7
635
const unsigned short & TransactionSpecification::getUdSubtype () const
636
{
637
  //## begin TransactionSpecification::getUdSubtype%4208AFAF01F7.body preserve=yes
638
 
639
	return ( m_udSubtype );
640
 
641
  //## end TransactionSpecification::getUdSubtype%4208AFAF01F7.body
642
}
643
 
644
//## Operation: getUdType%4208AFAF0245
645
const unsigned short & TransactionSpecification::getUdType () const
646
{
647
  //## begin TransactionSpecification::getUdType%4208AFAF0245.body preserve=yes
648
 
649
	return ( m_udType );
650
 
651
  //## end TransactionSpecification::getUdType%4208AFAF0245.body
652
}
653
 
654
//## Operation: getValues%41F705A600AC
655
const std::map< std::string, TransactionSpecificationValue * > & TransactionSpecification::getValues () const
656
{
657
  //## begin TransactionSpecification::getValues%41F705A600AC.body preserve=yes
658
 
659
	return ( m_value );
660
 
661
  //## end TransactionSpecification::getValues%41F705A600AC.body
662
}
663
 
664
//## Operation: isContained%41F70575014E
665
const bool TransactionSpecification::isContained (const std::string &xPath) const
666
{
667
  //## begin TransactionSpecification::isContained%41F70575014E.body preserve=yes
668
 
669
  return ( m_value.find( xPath ) != m_value.end() );
670
 
671
  //## end TransactionSpecification::isContained%41F70575014E.body
672
}
673
 
674
//## Operation: isMarked%41F708CB0307
675
const bool TransactionSpecification::isMarked (const std::string &xPath) const
676
{
677
  //## begin TransactionSpecification::isMarked%41F708CB0307.body preserve=yes
678
 
679
	std::map< std::string, TransactionSpecificationValue * >::const_iterator
680
		instance = m_value.find( xPath );
681
 
682
	if ( instance != m_value.end() )
683
	{
684
		return ( instance->second->isMarked() );
685
	}
686
	else
687
	{
688
		MTHROW( std::runtime_error, \
689
			"Cannot find value " << xPath << '.' );
690
	}
691
 
692
  //## end TransactionSpecification::isMarked%41F708CB0307.body
693
}
694
 
695
//## Operation: markValue%41F7069E002F
696
void TransactionSpecification::markValue (const std::string &xPath)
697
{
698
  //## begin TransactionSpecification::markValue%41F7069E002F.body preserve=yes
699
 
700
	std::map< std::string, TransactionSpecificationValue * >::const_iterator
701
		instance = m_value.find( xPath );
702
 
703
	if ( instance != m_value.end() )
704
	{
705
		instance->second->mark();
706
	}
707
	else
708
	{
709
		MTHROW( std::runtime_error, \
710
			"Cannot find value " << xPath << '.' );
711
	}
712
 
713
  //## end TransactionSpecification::markValue%41F7069E002F.body
714
}
715
 
716
//## Operation: setUdSubtype%42044110019A
717
const unsigned short & TransactionSpecification::setUdSubtype (const unsigned short &value)
718
{
719
  //## begin TransactionSpecification::setUdSubtype%42044110019A.body preserve=yes
720
 
721
	return ( m_udSubtype = value );
722
 
723
  //## end TransactionSpecification::setUdSubtype%42044110019A.body
724
}
725
 
726
//## Operation: setUdType%420440DE038E
727
const unsigned short & TransactionSpecification::setUdType (const unsigned short &value)
728
{
729
  //## begin TransactionSpecification::setUdType%420440DE038E.body preserve=yes
730
 
731
	return ( m_udType = value );
732
 
733
  //## end TransactionSpecification::setUdType%420440DE038E.body
734
}
735
 
736
//## Operation: evaluate%4205C6F500FC
737
const bool TransactionSpecification::evaluate (XMLSchema::IXmlSchemaWrapperElement &element, EvaluationContext& context)
738
{
739
  //## begin TransactionSpecification::evaluate%4205C6F500FC.body preserve=yes
740
 
741
	/**
742
	 *	Build an XPath from the name of the structure that we are traversing
743
	 *	right now and the xpath reported by the element being visited.  Then
744
	 *	look for a field with that XPath.
745
	 */
746
 
747
	std::stringstream xpath;
748
	if ( element.getAttributeValue( "xpath", *m_string ) )
749
	{
750
		xpath
751
			<< '/'
752
			<< m_structure[ m_structureIndex ]->getName()
753
			<< m_string->c_str();
754
 
755
		/**
756
		 *	Find the element if we have it.  We get calls for everything, not
757
		 *	just for what we have.  When we don't have the element, then we
758
		 *	have nothing to set, which is fine.
759
		 */
760
		std::map< std::string, TransactionSpecificationValue * >::iterator
761
			field = m_value.find( xpath.str() );
762
		if ( field != m_value.end() )
763
		{
764
			std::string value;
765
			bool postponed = false;
766
			if ( field->second->evaluate( value, true, context, postponed ) )
767
			{
768
				if ( !postponed )
769
				{
770
					*m_string = value.c_str();
771
					if ( element.setString( *m_string ) )
772
					{
773
						return ( true );
774
					}
775
					else
776
					{
777
						std::string datatype;
778
						if ( element.getAttributeValue( "datatype", *m_string ) )
779
						{
780
							datatype = m_string->c_str();
781
						}
782
 
783
						std::stringstream message;
784
						message
785
							<< "Cannot set value of \""
786
							<< xpath.str()
787
							<< "\" to \""
788
							<< value
789
							<< "\" as \""
790
							<< datatype
791
							<< "\".";
792
						MERROR( message.str() );
793
						message << "  Continue?";
794
 
795
						return ( MessageDlg(
796
									message.str().c_str(),
797
									mtConfirmation,
798
									TMsgDlgButtons() << mbYes << mbNo,
799
 
800
					}
801
				}
802
				else
803
				{
804
					return ( true );
805
				}
806
			}
807
			else
808
			{
809
				std::stringstream message;
810
				message
811
					<< "Cannot evaluate value of \"" \
812
					<< field->second->getExpression() \
813
					<< "\" for \"" \
814
					<< xpath.str() \
815
					<< "\".";
816
				MERROR( message.str() );
817
				message << "  Continue?";
818
 
819
				return ( MessageDlg(
820
							message.str().c_str(),
821
							mtConfirmation,
822
							TMsgDlgButtons() << mbYes << mbNo,
823
 
824
			}
825
		}
826
		else
827
		{
828
			// We have no value for this element, which is fine.
829
			return ( true );
830
		}
831
	}
832
	else
833
	{
834
		MERROR( "Cannot get xpath for schema element " << &element << '.' );
835
	}
836
 
837
	return ( false );
838
 
839
  //## end TransactionSpecification::evaluate%4205C6F500FC.body
840
}
841
 
842
// Additional Declarations
843
  //## begin TransactionSpecification%41F607FA0261.declarations preserve=yes
844
  //## end TransactionSpecification%41F607FA0261.declarations
845
 
846
//## begin module%41F607FA0261.epilog preserve=yes
847
//## end module%41F607FA0261.epilog