11using System ;
22using System . Diagnostics ;
33using System . IO ;
4+ using System . Linq ;
45using System . Threading ;
56using System . Threading . Tasks ;
67
@@ -27,75 +28,98 @@ public static async Task EmitAsync(StreamWriter writer, OperandsRegistry operand
2728 . WriteInitializerList ( )
2829 . BeginList ( ) ;
2930 var operandDeclaration = new ObjectDeclaration < InstructionOperand > ( ) ;
30- var opDeclaration = new SimpleObjectDeclaration ( InitializerType . Designated , "encoding" , "reg" , "mem" ) ;
31+ var sizes = operandsRegistry . Sizes . ToList ( ) ;
32+ var details = operandsRegistry . OperandsDetails . ToList ( ) ;
33+ Debug . Assert ( sizes . Count < byte . MaxValue ) ;
34+ Debug . Assert ( details . Count < byte . MaxValue ) ;
35+
36+ foreach ( var operand in operandsRegistry . Operands )
37+ {
38+ var operandEntry = operandsWriter . CreateObjectWriter ( operandDeclaration )
39+ . WriteExpression ( "type" , "ZYDIS_SEMANTIC_OPTYPE_{0}" , operand . Type . ToZydisString ( ) )
40+ . WriteExpression ( "visibility" , "ZYDIS_OPERAND_VISIBILITY_{0}" , operand . Visibility . ToZydisString ( ) )
41+ . WriteExpression ( "actions" , "ZYDIS_OPERAND_ACTION_{0}" , operand . Access . ToZydisString ( ) )
42+ . WriteExpression ( "element_type" , operand . ElementType . ToZydisString ( ) )
43+ . WriteBool ( "is_multisource4" , operand . IsMultiSource4 )
44+ . WriteBool ( "ignore_seg_override" , operand . IgnoreSegmentOverride )
45+ . WriteInteger ( "size_reference" , sizes . BinarySearch ( OperandsRegistry . GetSizeTable ( operand ) ) , 2 , true )
46+ . WriteInteger ( "details_reference" , details . BinarySearch ( OperandsRegistry . GetDetails ( operand ) ) , 2 , true ) ;
47+
48+ operandsWriter . WriteObject ( operandEntry ) ;
49+ }
50+
51+ operandsWriter . EndList ( ) ;
52+ declarationWriter . EndDeclaration ( ) ;
53+ declarationWriter . WriteNewline ( ) ;
54+ declarationWriter . WriteNewline ( ) ;
55+
56+ var sizesWriter = declarationWriter
57+ . BeginDeclaration ( "static const" , "ZyanU16" , "OPERAND_SIZES[][3]" )
58+ . WriteInitializerList ( )
59+ . BeginList ( ) ;
60+ var sizeArrayDeclaration = new ArrayObjectDeclaration ( 3 ) ;
61+
62+ foreach ( var sizeTable in sizes )
63+ {
64+ var sizeTableEntry = new ObjectWriter ( sizeArrayDeclaration , null )
65+ . WriteInteger ( 0 , sizeTable . Width16 )
66+ . WriteInteger ( 1 , sizeTable . Width32 )
67+ . WriteInteger ( 2 , sizeTable . Width64 ) ;
68+ sizesWriter . WriteObject ( sizeTableEntry ) ;
69+ }
70+
71+ sizesWriter . EndList ( ) ;
72+ declarationWriter . EndDeclaration ( ) ;
73+ declarationWriter . WriteNewline ( ) ;
74+ declarationWriter . WriteNewline ( ) ;
75+
76+ var detailsWriter = declarationWriter
77+ . BeginDeclaration ( "static const" , "ZydisOperandDetails" , "OPERAND_DETAILS[]" )
78+ . WriteInitializerList ( )
79+ . BeginList ( ) ;
80+ var detailsDeclaration = new SimpleObjectDeclaration ( InitializerType . Designated , "encoding" , "reg" , "mem" ) ;
3181 var regOuterDeclaration = new SimpleObjectDeclaration ( "type" , "reg" ) ;
3282 var regInnerDeclaration = new SimpleObjectDeclaration ( InitializerType . Designated , "reg" , "id" ) ;
3383 var memDeclaration = new SimpleObjectDeclaration ( "seg" , "base" ) ;
3484
35- foreach ( var operand in operandsRegistry . Operands )
85+ foreach ( var opDetails in details )
3686 {
37- var operandEntry = operandsWriter . CreateObjectWriter ( operandDeclaration ) ;
38- var opEntry = operandEntry . CreateObjectWriter ( opDeclaration ) ;
39- if ( operand . Type is OperandType . ImplicitReg )
87+ var detailsEntry = detailsWriter . CreateObjectWriter ( detailsDeclaration ) ;
88+ if ( opDetails . Type == "MEMORY" )
89+ {
90+ var memEntry = detailsEntry . CreateObjectWriter ( memDeclaration ) ;
91+ memEntry
92+ . WriteInteger ( "seg" , ( int ) ( opDetails . MemorySegment ?? SegmentRegister . None ) )
93+ . WriteExpression ( "base" , opDetails . MemoryBase ! . Value . ToZydisString ( ) ) ;
94+ detailsEntry . WriteObject ( "mem" , memEntry ) ;
95+ }
96+ else if ( opDetails . Type == "OTHER" )
97+ {
98+ detailsEntry . WriteExpression ( "encoding" , "ZYDIS_OPERAND_ENCODING_{0}" , opDetails . Encoding . ToZydisString ( ) ) ;
99+ }
100+ else
40101 {
41- var regOuterEntry = opEntry . CreateObjectWriter ( regOuterDeclaration ) ;
102+ var regOuterEntry = detailsEntry . CreateObjectWriter ( regOuterDeclaration ) ;
42103 var regInnerEntry = regOuterEntry . CreateObjectWriter ( regInnerDeclaration ) ;
43- var type = operand . Register . GetRegisterClass ( ) switch
44- {
45- RegisterClass . GPROSZ => "GPR_OSZ" ,
46- RegisterClass . GPRASZ => "GPR_ASZ" ,
47- RegisterClass . GPRSSZ => "GPR_SSZ" ,
48- _ => "STATIC"
49- } ;
50- type = operand . Register switch
51- {
52- Register . ASZIP => "IP_ASZ" ,
53- Register . SSZIP => "IP_SSZ" ,
54- Register . SSZFLAGS => "FLAGS_SSZ" ,
55- _ => type
56- } ;
57104
58- if ( type == "STATIC" )
105+ if ( opDetails . Type == "STATIC" )
59106 {
60- regInnerEntry . WriteExpression ( "reg" , "ZYDIS_REGISTER_{0}" , operand . Register . ToZydisString ( ) ) ;
107+ regInnerEntry . WriteExpression ( "reg" , "ZYDIS_REGISTER_{0}" , opDetails . Register . ToZydisString ( ) ) ;
61108 regOuterEntry . WriteExpression ( "type" , "ZYDIS_IMPLREG_TYPE_STATIC" ) ;
62-
63109 }
64110 else
65111 {
66- regInnerEntry . WriteInteger ( "id" , operand . Register . GetRegisterId ( ) & 0x3F , 4 , true ) ;
67- regOuterEntry . WriteExpression ( "type" , "ZYDIS_IMPLREG_TYPE_{0}" , type ) ;
112+ regInnerEntry . WriteInteger ( "id" , opDetails . Register . GetRegisterId ( ) & 0x3F , 4 , true ) ;
113+ regOuterEntry . WriteExpression ( "type" , "ZYDIS_IMPLREG_TYPE_{0}" , opDetails . Type ) ;
68114 }
69115
70116 regOuterEntry . WriteObject ( "reg" , regInnerEntry ) ;
71- opEntry . WriteObject ( "reg" , regOuterEntry ) ;
72- }
73- else if ( operand . Type is OperandType . ImplicitMem )
74- {
75- var memEntry = opEntry . CreateObjectWriter ( memDeclaration ) ;
76- memEntry
77- . WriteInteger ( "seg" , ( int ) ( operand . MemorySegment ?? SegmentRegister . None ) )
78- . WriteExpression ( "base" , operand . MemoryBase ! . Value . ToZydisString ( ) ) ;
79- opEntry . WriteObject ( "mem" , memEntry ) ;
80- }
81- else
82- {
83- opEntry . WriteExpression ( "encoding" , "ZYDIS_OPERAND_ENCODING_{0}" , operand . Encoding . ToZydisString ( ) ) ;
117+ detailsEntry . WriteObject ( "reg" , regOuterEntry ) ;
84118 }
85- operandEntry
86- . WriteExpression ( "type" , "ZYDIS_SEMANTIC_OPTYPE_{0}" , operand . Type . ToZydisString ( ) )
87- . WriteExpression ( "visibility" , "ZYDIS_OPERAND_VISIBILITY_{0}" , operand . Visibility . ToZydisString ( ) )
88- . WriteExpression ( "actions" , "ZYDIS_OPERAND_ACTION_{0}" , operand . Access . ToZydisString ( ) )
89- . WriteIntegerArray ( "size" , operand . Width16 , operand . Width32 , operand . Width64 )
90- . WriteExpression ( "element_type" , operand . ElementType . ToZydisString ( ) )
91- . WriteObject ( "op" , opEntry )
92- . WriteBool ( "is_multisource4" , operand . IsMultiSource4 )
93- . WriteBool ( "ignore_seg_override" , operand . IgnoreSegmentOverride ) ;
94-
95- operandsWriter . WriteObject ( operandEntry ) ;
119+ detailsWriter . WriteObject ( detailsEntry ) ;
96120 }
97121
98- operandsWriter . EndList ( ) ;
122+ detailsWriter . EndList ( ) ;
99123 declarationWriter . EndDeclaration ( ) ;
100124
101125 await writer . WriteLineAsync ( ) . ConfigureAwait ( false ) ;
0 commit comments