OpenASIP 2.2
Loading...
Searching...
No Matches
Protected Member Functions | Private Member Functions | Static Private Attributes | List of all members
TPEF::TPEFCodeSectionWriter Class Reference

#include <TPEFCodeSectionWriter.hh>

Inheritance diagram for TPEF::TPEFCodeSectionWriter:
Inheritance graph
Collaboration diagram for TPEF::TPEFCodeSectionWriter:
Collaboration graph

Protected Member Functions

 TPEFCodeSectionWriter ()
 
virtual ~TPEFCodeSectionWriter ()
 
virtual Section::SectionType type () const
 
virtual void actualWriteData (BinaryStream &stream, const Section *sect) const
 
virtual void writeInfo (BinaryStream &stream, const Section *sect) const
 
virtual void writeId (BinaryStream &stream, HalfWord id) const
 
- Protected Member Functions inherited from TPEF::TPEFSectionWriter
 TPEFSectionWriter ()
 
virtual ~TPEFSectionWriter ()
 
virtual const BinaryWriterparent () const
 
virtual void actualWriteHeader (BinaryStream &stream, const Section *sect) const
 
virtual void createKeys (const Section *sect) const
 
virtual void writeSize (BinaryStream &stream, const Section *sect) const
 
virtual SectionId getSectionId () const
 
virtual Word elementSize (const Section *section) const
 
- Protected Member Functions inherited from TPEF::SectionWriter
 SectionWriter ()
 
virtual ~SectionWriter ()
 
virtual void finalize (BinaryStream &stream, Section *section) const
 

Private Member Functions

 TPEFCodeSectionWriter (const TPEFCodeSectionWriter &)
 Copying not allowed.
 
TPEFCodeSectionWriteroperator= (const TPEFCodeSectionWriter &)
 Assignment not allowed.
 
void writeAttributeField (BinaryStream &stream, SectionElement *elem, bool isEnd) const
 
void writeDataField (BinaryStream &stream, SectionElement *elem) const
 
void writeAnnotations (BinaryStream &stream, SectionElement *elem) const
 

Static Private Attributes

static const TPEFCodeSectionWriter instance_
 Unique instance of class.
 
static const Byte IMMEDIATE_VALUE_MAX_BYTES = 16
 Maximum number of bytes that single immediate can contain.
 

Additional Inherited Members

- Static Public Member Functions inherited from TPEF::SectionWriter
static void writeHeader (BinaryStream &stream, const Section *sect, const BinaryWriter *writer)
 
static void writeData (BinaryStream &stream, const Section *sect, const BinaryWriter *writer)
 
static void finalizeBinary (BinaryStream &stream, const Binary *binaryToFinalize, const BinaryWriter *writer)
 
- Static Protected Member Functions inherited from TPEF::SectionWriter
static void registerSectionWriter (const SectionWriter *sWriter)
 
static SectionId getUniqueSectionId ()
 

Detailed Description

Writes TPEF code section to file.

Definition at line 48 of file TPEFCodeSectionWriter.hh.

Constructor & Destructor Documentation

◆ TPEFCodeSectionWriter() [1/2]

TPEF::TPEFCodeSectionWriter::TPEFCodeSectionWriter ( )
protected

Constructor.

Registers itself to SectionWriter.

Definition at line 64 of file TPEFCodeSectionWriter.cc.

66}
static void registerSectionWriter(const SectionWriter *sWriter)

References TPEF::SectionWriter::registerSectionWriter().

Here is the call graph for this function:

◆ ~TPEFCodeSectionWriter()

TPEF::TPEFCodeSectionWriter::~TPEFCodeSectionWriter ( )
protectedvirtual

Destructor.

Definition at line 71 of file TPEFCodeSectionWriter.cc.

71 {
72}

◆ TPEFCodeSectionWriter() [2/2]

TPEF::TPEFCodeSectionWriter::TPEFCodeSectionWriter ( const TPEFCodeSectionWriter )
private

Copying not allowed.

Member Function Documentation

◆ actualWriteData()

void TPEF::TPEFCodeSectionWriter::actualWriteData ( BinaryStream stream,
const Section sect 
) const
protectedvirtual

Writes the data of the section to stream.

Parameters
streamThe stream to be written to.
sectThe section to be written.

Reimplemented from TPEF::TPEFSectionWriter.

Definition at line 91 of file TPEFCodeSectionWriter.cc.

93 {
94
95 // file offset to data of section
96 FileOffset startOffset = stream.writePosition();
97
98 SectionOffset sectOffset = 0;
99
100 SectionKey sKey = SafePointer::sectionKeyFor(sect);
101 SectionId id = sKey.sectionId();
102
103 for (Word i = 0; i < sect->elementCount(); i++) {
104 InstructionElement *elem =
105 dynamic_cast<InstructionElement*>(sect->element(i));
106
107 assert(elem != NULL);
108
109 sectOffset = stream.writePosition() - startOffset;
110
111 if (SafePointer::isReferenced(elem) || i == 0) {
113 SectionOffsetKey(id, sectOffset), elem);
114 }
115
116 // check if this is ending move of instruction
117 bool isEnd = false;
118 i++;
119 if (i == sect->elementCount() ||
120 dynamic_cast<InstructionElement*>(sect->element(i))->begin()) {
121
122 isEnd = true;
123 }
124 i--;
125
126 writeAttributeField(stream, elem, isEnd);
127 writeDataField(stream, elem);
128 writeAnnotations(stream, elem);
129 }
130
131 // section body offset
133 FileOffsetKey(startOffset), sect->element(0));
134
135 SectionSizeReplacer::setSize(sect, stream.writePosition() - startOffset);
136}
#define assert(condition)
static void addObjectReference(SectionIndexKey key, const SafePointable *obj)
static SectionKey sectionKeyFor(const SafePointable *obj)
static bool isReferenced(const SafePointable *object)
static void setSize(const SafePointable *obj, Word size)
void writeAttributeField(BinaryStream &stream, SectionElement *elem, bool isEnd) const
void writeAnnotations(BinaryStream &stream, SectionElement *elem) const
void writeDataField(BinaryStream &stream, SectionElement *elem) const
HalfWord SectionId
Type for storing binary file section ids.
Word SectionOffset
Type for storing offsets relative to a given base offset value.
Word FileOffset
Type for storing absolute file offsets.

References TPEF::ReferenceManager::SafePointer::addObjectReference(), assert, TPEF::InstructionElement::begin(), TPEF::Section::element(), TPEF::Section::elementCount(), TPEF::ReferenceManager::SafePointer::isReferenced(), TPEF::ReferenceManager::SectionKey::sectionId(), TPEF::ReferenceManager::SafePointer::sectionKeyFor(), TPEF::SectionSizeReplacer::setSize(), writeAnnotations(), writeAttributeField(), writeDataField(), and TPEF::BinaryStream::writePosition().

Here is the call graph for this function:

◆ operator=()

TPEFCodeSectionWriter & TPEF::TPEFCodeSectionWriter::operator= ( const TPEFCodeSectionWriter )
private

Assignment not allowed.

◆ type()

Section::SectionType TPEF::TPEFCodeSectionWriter::type ( ) const
protectedvirtual

Returns the type of section that this writer writes.

Returns
The type of section that this writer writes.

Implements TPEF::TPEFSectionWriter.

Definition at line 80 of file TPEFCodeSectionWriter.cc.

80 {
81 return Section::ST_CODE;
82}
@ ST_CODE
Text section.
Definition Section.hh:79

References TPEF::Section::ST_CODE.

◆ writeAnnotations()

void TPEF::TPEFCodeSectionWriter::writeAnnotations ( BinaryStream stream,
SectionElement elem 
) const
private

Writes annotations to stream if there are any.

Parameters
streamStream to write.
elemElement, whose annotations are written.

Definition at line 304 of file TPEFCodeSectionWriter.cc.

306 {
307
308 InstructionElement *instr = dynamic_cast<InstructionElement*>(elem);
309
310 for (Word i = 0; i < instr->annotationCount(); i++) {
311
312 InstructionAnnotation* annotation = instr->annotation(i);
313
314 Byte sizeAndContinuation =
315 annotation->size() & TPEFHeaders::IANNOTE_SIZE;
316
317 // if not last annotation
318 if (i != (instr->annotationCount() - 1)) {
319 sizeAndContinuation =
320 sizeAndContinuation | TPEFHeaders::IANNOTE_CONTINUATION;
321 }
322
323 stream.writeByte(sizeAndContinuation);
324
325 // write identification code in big endian format
326 // NOTE: should there be function in
327 // BinaryStream to write 3 byte "word"s?
328 stream.writeByte(annotation->id() & 0xff);
329 stream.writeByte((annotation->id() >> (BYTE_BITWIDTH)) & 0xff);
330 stream.writeByte((annotation->id() >> (BYTE_BITWIDTH*2)) & 0xff);
331
332 // write payload
333 for (Word j = 0; j < annotation->size(); j++) {
334 stream.writeByte(annotation->byte(j));
335 }
336 }
337}
const Byte BYTE_BITWIDTH
Definition BaseType.hh:136
unsigned char Byte
Definition BaseType.hh:116
@ IANNOTE_SIZE
Size of payload of annotation.
@ IANNOTE_CONTINUATION
If there is more annotations.

References TPEF::InstructionElement::annotation(), TPEF::InstructionElement::annotationCount(), TPEF::InstructionAnnotation::byte(), BYTE_BITWIDTH, TPEF::TPEFHeaders::IANNOTE_CONTINUATION, TPEF::TPEFHeaders::IANNOTE_SIZE, TPEF::InstructionAnnotation::id(), TPEF::InstructionAnnotation::size(), and TPEF::BinaryStream::writeByte().

Referenced by actualWriteData().

Here is the call graph for this function:

◆ writeAttributeField()

void TPEF::TPEFCodeSectionWriter::writeAttributeField ( BinaryStream stream,
SectionElement elem,
bool  isEnd 
) const
private

Writes the attribute field of either move or immediate.

Parameters
streamThe stream to be written to.
elemThe element to be written out.

Definition at line 145 of file TPEFCodeSectionWriter.cc.

148 {
149
150 Byte attribute = 0;
151
152 if (dynamic_cast<InstructionElement*>(elem)->isMove()) {
153
154 MoveElement* move = dynamic_cast<MoveElement*>(elem);
155
156 if (move->isGuarded()) {
157 attribute = attribute | TPEFHeaders::IA_MGUARD;
158 }
159
160 if (move->isEmpty()) {
161 attribute = attribute | TPEFHeaders::IA_EMPTY;
162 }
163
164 } else if (dynamic_cast<InstructionElement*>(elem)->isImmediate()) {
165
166 ImmediateElement* imm = dynamic_cast<ImmediateElement*>(elem);
167
168 // immediate type flag
169 attribute = attribute | TPEFHeaders::IA_TYPE;
170
171 // length of immediate is stored in 4 first bits of byte.
172 Byte immLength = imm->length();
173 Byte immBits = (immLength << (BYTE_BITWIDTH / 2));
174
175 attribute = attribute | immBits;
176
177 } else {
178 bool impossibleInstructionElementType = false;
179 assert(impossibleInstructionElementType);
180 }
181
182 if (dynamic_cast<InstructionElement*>(elem)->annotationCount() > 0) {
183 attribute = attribute | TPEFHeaders::IA_ANNOTE;
184 }
185
186 if (isEnd) {
187 attribute = attribute | TPEFHeaders::IA_END;
188 }
189
190 stream.writeByte(attribute);
191}
@ IA_END
Is end of instruction.
@ IA_MGUARD
Is conditional move or unconditional move.
@ IA_TYPE
Instruction type: move (0), immediate (1).
@ IA_ANNOTE
Contains annotation.
@ IA_EMPTY
Empty instruction.

References assert, BYTE_BITWIDTH, TPEF::TPEFHeaders::IA_ANNOTE, TPEF::TPEFHeaders::IA_EMPTY, TPEF::TPEFHeaders::IA_END, TPEF::TPEFHeaders::IA_MGUARD, TPEF::TPEFHeaders::IA_TYPE, TPEF::MoveElement::isEmpty(), TPEF::MoveElement::isGuarded(), TPEF::InstructionElement::isImmediate(), TPEF::ImmediateElement::length(), and TPEF::BinaryStream::writeByte().

Referenced by actualWriteData().

Here is the call graph for this function:

◆ writeDataField()

void TPEF::TPEFCodeSectionWriter::writeDataField ( BinaryStream stream,
SectionElement elem 
) const
private

Writes the data portion of either move or immediate element.

Parameters
streamThe stream to be written to.
elemThe element to be written.

Definition at line 200 of file TPEFCodeSectionWriter.cc.

202 {
203
204 if (dynamic_cast<InstructionElement*>(elem)->isMove()) {
205 MoveElement* move = dynamic_cast<MoveElement*>(elem);
206
207 writeId(stream, move->bus());
208
209 Byte fieldTypes = 0;
210
211 if (!move->isEmpty()) {
212
213 switch(move->sourceType()) {
215 fieldTypes |= TPEFHeaders::MVS_RF;
216 break;
218 fieldTypes |= TPEFHeaders::MVS_IMM;
219 break;
221 fieldTypes |= TPEFHeaders::MVS_UNIT;
222 break;
223 default:
224 std::cerr << "move source type: " << std::hex
225 << (int)move->sourceType() << std::dec << std::endl;
226 assert(false);
227 }
228
229 switch(move->destinationType()) {
231 fieldTypes |= TPEFHeaders::MVD_RF;
232 break;
234 fieldTypes |= TPEFHeaders::MVD_UNIT;
235 break;
236 default:
237 std::cerr << "move dest type: "
238 << (int)move->destinationType()
239 << "\tdest unit: "
240 << (int)move->destinationUnit()
241 << "\tindex: "
242 << (int)move->destinationIndex()
243 << std::endl;
244
245 assert(false);
246 }
247
248 if (move->isGuarded()) {
249 switch(move->guardType()) {
251 fieldTypes |= TPEFHeaders::MVG_RF;
252 break;
254 fieldTypes |= TPEFHeaders::MVG_UNIT;
255 break;
256 default:
257 std::cerr << "move guarde type: " << std::hex
258 << (int)move->guardType()
259 << std::dec << std::endl;
260 assert(false);
261 }
262
263 if (move->isGuardInverted() != 0) {
264 fieldTypes |= TPEFHeaders::IE_GUARD_INV_MASK;
265
266 }
267 }
268 }
269
270 stream.writeByte(fieldTypes);
271
272 writeId(stream, move->sourceUnit());
273 stream.writeHalfWord(move->sourceIndex());
274
275 writeId(stream, move->destinationUnit());
276 stream.writeHalfWord(move->destinationIndex());
277
278 writeId(stream, move->guardUnit());
279 stream.writeHalfWord(move->guardIndex());
280
281 } else {
282 ImmediateElement* imm = dynamic_cast<ImmediateElement*>(elem);
283 Byte dstUnit = imm->destinationUnit();
284 Byte dstIndex = imm->destinationIndex();
285
286 stream.writeByte(dstUnit);
287 stream.writeByte(dstIndex);
288
289 assert(imm->length() <= IMMEDIATE_VALUE_MAX_BYTES);
290
291 for (unsigned int i = 0; i < imm->length(); i++) {
292 stream.writeByte(imm->byte(i));
293 }
294 }
295}
@ MF_RF
Register file.
@ MF_IMM
Immediate.
@ MF_UNIT
Function unit.
virtual void writeId(BinaryStream &stream, HalfWord id) const
static const Byte IMMEDIATE_VALUE_MAX_BYTES
Maximum number of bytes that single immediate can contain.
@ IE_GUARD_INV_MASK
Guard inverted (1) means inverted.
@ MVG_RF
Guard is RF.
@ MVD_UNIT
Destination is FU.
@ MVS_IMM
Source is immediate.
@ MVD_RF
Destination is RF.
@ MVS_UNIT
Source is FU.
@ MVG_UNIT
Guard is FU.
@ MVS_RF
Source is RF.

References assert, TPEF::MoveElement::bus(), TPEF::ImmediateElement::byte(), TPEF::ImmediateElement::destinationIndex(), TPEF::MoveElement::destinationIndex(), TPEF::MoveElement::destinationType(), TPEF::ImmediateElement::destinationUnit(), TPEF::MoveElement::destinationUnit(), TPEF::MoveElement::guardIndex(), TPEF::MoveElement::guardType(), TPEF::MoveElement::guardUnit(), TPEF::TPEFHeaders::IE_GUARD_INV_MASK, IMMEDIATE_VALUE_MAX_BYTES, TPEF::MoveElement::isEmpty(), TPEF::MoveElement::isGuarded(), TPEF::MoveElement::isGuardInverted(), TPEF::ImmediateElement::length(), TPEF::MoveElement::MF_IMM, TPEF::MoveElement::MF_RF, TPEF::MoveElement::MF_UNIT, TPEF::TPEFHeaders::MVD_RF, TPEF::TPEFHeaders::MVD_UNIT, TPEF::TPEFHeaders::MVG_RF, TPEF::TPEFHeaders::MVG_UNIT, TPEF::TPEFHeaders::MVS_IMM, TPEF::TPEFHeaders::MVS_RF, TPEF::TPEFHeaders::MVS_UNIT, TPEF::MoveElement::sourceIndex(), TPEF::MoveElement::sourceType(), TPEF::MoveElement::sourceUnit(), TPEF::BinaryStream::writeByte(), TPEF::BinaryStream::writeHalfWord(), and writeId().

Referenced by actualWriteData().

Here is the call graph for this function:

◆ writeId()

void TPEF::TPEFCodeSectionWriter::writeId ( BinaryStream stream,
HalfWord  id 
) const
protectedvirtual

Writes Bus, FU or RF id according to TPEF version.

Original TPEF version 1 supports only less than 256 buses, FUs and RFs. Version 2 fixes that issue and we need to check the stream version for proper amount of bytes to write.

Parameters
streamStream to which the data is written.
sectid of the component.

Definition at line 372 of file TPEFCodeSectionWriter.cc.

372 {
373
374 TPEFHeaders::TPEFVersion version = stream.TPEFVersion();
375
376 if (version == TPEFHeaders::TPEFVersion::TPEF_V1) {
377 stream.writeByte(id);
378 } else {
379 stream.writeHalfWord(id);
380 }
381}
@ TPEF_V1
Initial TPEF version.

References TPEF::TPEFHeaders::TPEF_V1, TPEF::BinaryStream::TPEFVersion(), TPEF::BinaryStream::writeByte(), and TPEF::BinaryStream::writeHalfWord().

Referenced by writeDataField().

Here is the call graph for this function:

◆ writeInfo()

void TPEF::TPEFCodeSectionWriter::writeInfo ( BinaryStream stream,
const Section sect 
) const
protectedvirtual

Writes the ‘info’ field of code section header.

The ‘info’ field of code sections normally contains information related to instruction size and encoding. The TUT_TTA architecture does not use this field and ignores its contents.

Parameters
streamStream to which the data is written.
sectInput section. Unused.

Reimplemented from TPEF::TPEFSectionWriter.

Definition at line 351 of file TPEFCodeSectionWriter.cc.

353 {
354
355 stream.writeHalfWord(0); // unused field
356 stream.writeByte(0); // unused field - must be set to zero!
357 stream.writeByte(0); // padding
358}

References TPEF::BinaryStream::writeByte(), and TPEF::BinaryStream::writeHalfWord().

Here is the call graph for this function:

Member Data Documentation

◆ IMMEDIATE_VALUE_MAX_BYTES

const Byte TPEF::TPEFCodeSectionWriter::IMMEDIATE_VALUE_MAX_BYTES = 16
staticprivate

Maximum number of bytes that single immediate can contain.

Definition at line 80 of file TPEFCodeSectionWriter.hh.

Referenced by writeDataField().

◆ instance_

const TPEFCodeSectionWriter TPEF::TPEFCodeSectionWriter::instance_
staticprivate

Unique instance of class.

Definition at line 78 of file TPEFCodeSectionWriter.hh.


The documentation for this class was generated from the following files: