~george-edison55/7basic/trunk

« back to all changes in this revision

Viewing changes to CELFOutput.cpp

  • Committer: Nathan
  • Date: 2010-09-29 20:58:50 UTC
  • Revision ID: nathan@nathan-laptop-20100929205850-iosfb9bbpo0vphma
Moving output code - Part 9

Show diffs side-by-side

added added

removed removed

Lines of Context:
32
32
    WriteInstruction(X86_PUSH,&p1);
33
33
}
34
34
 
35
 
void CELFOutput::WritePushFloatInstruction(float)
 
35
void CELFOutput::WritePushFloatInstruction(float fVal)
36
36
{
37
 
    //...
 
37
    // To push a float onto the stack, we have to
 
38
    // register the constant in the float literal
 
39
    // list and then push the two parts of it
 
40
    // onto the stack
 
41
 
 
42
    const char * pName = RegisterFloatLiteral(fVal).c_str();
 
43
 
 
44
    // Now we simply push the value returned
 
45
    // using two push instructions
 
46
 
 
47
    CInstructionParameter p1;
 
48
    p1.iType = PT_DWORD_SYMBOL_4;
 
49
    p1.value.pString = pName;
 
50
 
 
51
    WriteInstruction(X86_PUSH,&p1);
 
52
 
 
53
    p1.iType = PT_DWORD_SYMBOL;
 
54
 
 
55
    WriteInstruction(X86_PUSH,&p1);
38
56
}
39
57
 
40
58
void CELFOutput::WritePushStringInstruction(std::string str)
60
78
 
61
79
    if(pSrc->type->iType == VT_FLOAT)
62
80
    {
63
 
        // TODO: unimplemented
 
81
        CInstructionParameter p1;
 
82
        p1.iType = PT_DWORD_VALUE_4;
 
83
        p1.value.iOffset = pSrc->offset;
 
84
 
 
85
        WriteInstruction(X86_PUSH,&p1);
 
86
 
 
87
        p1.iType = PT_DWORD_VALUE;
 
88
 
 
89
        WriteInstruction(X86_PUSH,&p1);
64
90
    }
65
91
    else
66
92
    {
98
124
 
99
125
    if(pDest->type->iType == VT_FLOAT)
100
126
    {
101
 
        // TODO: unimplemented
102
 
 
103
 
        //  m_str << "pop dword [v_" << pDest->offset << "]" << std::endl;
104
 
        // m_str << "pop dword [v_" << pDest->offset << "+4]" << std::endl;
 
127
        CInstructionParameter p1;
 
128
        p1.iType = PT_DWORD_VALUE_4;
 
129
        p1.value.iOffset = pDest->offset;
 
130
 
 
131
        WriteInstruction(X86_POP,&p1);
 
132
 
 
133
        p1.iType = PT_DWORD_VALUE;
 
134
 
 
135
        WriteInstruction(X86_POP,&p1);
105
136
    }
106
137
    else
107
138
    {
252
283
 
253
284
void CELFOutput::WriteFloatAddInstruction()
254
285
{
255
 
    //...
 
286
    WriteFloatArithmeticInstruction(X86_FADDP);
256
287
}
257
288
 
258
289
void CELFOutput::WriteFloatSubInstruction()
259
290
{
260
 
    //...
 
291
    WriteFloatArithmeticInstruction(X86_FSUBRP);
261
292
}
262
293
 
263
294
void CELFOutput::WriteFloatMulInstruction()
264
295
{
265
 
    //...
 
296
    WriteFloatArithmeticInstruction(X86_FMULP);
266
297
}
267
298
 
268
299
void CELFOutput::WriteFloatDivInstruction()
269
300
{
270
 
    //...
 
301
    WriteFloatArithmeticInstruction(X86_FDIVRP);
271
302
}
272
303
 
273
304
void CELFOutput::WriteFloatLessInstruction()
487
518
 
488
519
void CELFOutput::WritePrintFloatInstruction()
489
520
{
490
 
    //...
 
521
    // This one is easy. Just print it!
 
522
 
 
523
    // Well, first we push the format string.
 
524
 
 
525
    CInstructionParameter p1;
 
526
    p1.iType = PT_STRING;
 
527
    p1.value.pString = "printf_f";
 
528
 
 
529
    WriteInstruction(X86_PUSH,&p1);
 
530
 
 
531
    WriteCallInstruction("printf",12);
491
532
}
492
533
 
493
534
void CELFOutput::WritePrintStringInstruction()
506
547
    WriteCallInstruction("printf",8);
507
548
}
508
549
 
509
 
 
510
550
void CELFOutput::WriteInputIntegerInstruction(CVar * pVar)
511
551
{
512
552
    // We need to load the address of the integer
530
570
    WriteCallInstruction("scanf",8);
531
571
}
532
572
 
533
 
void CELFOutput::WriteInputFloatInstruction(CVar *)
 
573
void CELFOutput::WriteInputFloatInstruction(CVar * pVar)
534
574
{
535
 
    //...
 
575
    // We should simply have to push the address of the
 
576
    // float onto the stack
 
577
 
 
578
    CInstructionParameter p1;
 
579
    p1.iType = PT_REGISTER;
 
580
    p1.value.iRegister = REGISTER_EAX;
 
581
 
 
582
    CInstructionParameter p2;
 
583
    p2.iType = PT_OFFSET;
 
584
    p2.value.iOffset = pVar->offset;
 
585
 
 
586
    WriteInstruction(X86_LEA,&p1,&p2);
 
587
 
 
588
    WritePushRegisterInstruction(REGISTER_EAX);
 
589
 
 
590
    // Now push the format string
 
591
 
 
592
    p1.iType = PT_STRING;
 
593
    p1.value.pString = "scanf_f";
 
594
 
 
595
    WriteInstruction(X86_PUSH,&p1);
 
596
 
 
597
    // Now call scanf
 
598
 
 
599
    WriteCallInstruction("scanf",8);
536
600
}
537
601
 
538
602
void CELFOutput::WriteInputStringInstruction(CVar * pVar)
735
799
 
736
800
    WriteLabel(l2);
737
801
}
 
802
 
 
803
void CELFOutput::WriteFloatArithmeticInstruction(X86_OPCODE op)
 
804
{
 
805
    // The first step here is to pop the two floats
 
806
    // on top of the stack
 
807
 
 
808
    CInstructionParameter p1;
 
809
 
 
810
    // We do this twice
 
811
 
 
812
    for(int i=0;i<2;++i)
 
813
    {
 
814
        // Start by popping the top into our temp. float
 
815
 
 
816
        p1.iType = PT_DWORD_VALUE;
 
817
        p1.value.iOffset = 4;
 
818
 
 
819
        WriteInstruction(X86_POP,&p1);
 
820
 
 
821
        p1.iType = PT_DWORD_VALUE_4;
 
822
 
 
823
        WriteInstruction(X86_POP,&p1);
 
824
 
 
825
        // Now load this onto the FPU stack
 
826
 
 
827
        p1.iType = PT_QWORD;
 
828
 
 
829
        WriteInstruction(X86_FLD,&p1);
 
830
 
 
831
        // Now repeat those steps a second time
 
832
    }
 
833
 
 
834
    // Now we perform the operation
 
835
 
 
836
    p1.iType = PT_ST_VAL;
 
837
    p1.value.iST = 1;
 
838
 
 
839
    CInstructionParameter p2;
 
840
    p2.iType = PT_ST_VAL;
 
841
    p2.value.iST = 0;
 
842
 
 
843
    WriteInstruction(op,&p1,&p2);
 
844
 
 
845
    // Now we pop the results off of the FPU stack
 
846
 
 
847
    p1.iType = PT_QWORD;
 
848
    p1.value.iOffset = 4;
 
849
 
 
850
    WriteInstruction(X86_FSTP,&p1);
 
851
 
 
852
    // Now push it back onto the stack
 
853
 
 
854
    p1.iType = PT_DWORD_VALUE_4;
 
855
 
 
856
    WriteInstruction(X86_PUSH,&p1);
 
857
 
 
858
    p1.iType = PT_DWORD_VALUE;
 
859
 
 
860
    WriteInstruction(X86_PUSH,&p1);
 
861
}
 
862
 
 
863
void CELFOutput::WriteFloatLogicInstruction(X86_OPCODE)
 
864
{
 
865
    //...
 
866
}