Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(6)

Side by Side Diff: src/trusted/validator/x86/testing/enuminsts/input_tester.c

Issue 9861030: Modify enuminsts to be able to communicate matched instructions accross (Closed) Base URL: svn://svn.chromium.org/native_client/trunk/src/native_client/
Patch Set: Created 8 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
(Empty)
1 /*
2 * Copyright (c) 2012 The Native Client Authors. All rights reserved.
3 * Use of this source code is governed by a BSD-style license that can be
4 * found in the LICENSE file.
5 */
6
7 /*
8 * input_tester.c
9 * Implements a decoder that matches the input enumeration fed into stdin.
10 */
11
12 #include "native_client/src/trusted/validator/x86/testing/enuminsts/input_tester .h"
13
14 #include <stdio.h>
15 #include <string.h>
16
17 #include "native_client/src/trusted/validator/types_memory_model.h"
18 #include "native_client/src/trusted/validator/x86/ncinstbuffer.h"
19 #include "native_client/src/trusted/validator/x86/testing/enuminsts/str_utils.h"
20 #include "native_client/src/trusted/validator/x86/testing/enuminsts/text2hex.h"
21
22 #define kBufferSize 1024
23
24 /* Defines the virtual table for the input decoder. */
25 static struct {
26 /* The virtual table that implements this decoder. */
27 NaClEnumeratorDecoder base_;
28 /* The iput text line. */
29 char line_[kBufferSize];
30 /* The number of bytes in the last instruction read from the
31 * input stream.
32 */
33 int num_bytes_;
34 /* The input line number associated with the last instruction
35 * read from the input stream.
36 */
37 int line_number_;
38 /* The specified pc address when parsing. */
39 NaClPcAddress pc_address_;
40 /* The instruction mnemonic, if defined. */
41 char* mnemonic_;
42 /* The instruction arguments, if defined. */
43 char* operands_;
44 /* Buffer used to hold mnemonic name and operands. */
45 char buffer_[kBufferSize];
46 /* Boolean flag defining if we have processed the first
47 * line of input, which specifies how to configure the
48 * the input decoder.
49 */
50 Bool configured_;
51 } input_decoder;
52
53 /* Defines the function to parse the first instruction in the enumerator
54 * text. Since we are accepting the input that was set up the input
55 * enumeration, there is nothing to do.
56 */
57 static void ParseInst(const NaClEnumerator* enumerator,
58 const int pc_address) {
59 input_decoder.pc_address_ = pc_address;
60 input_decoder.mnemonic_ = NULL;
61 input_decoder.operands_ = NULL;
62 }
63
64 /* Finds the instruction mnemonic, by looking at the end of the
65 * input line. Looks for a comment of the form '#mnemonic operands'
66 */
67 static void AssembleDesc(const NaClEnumerator* enumerator) {
68 char* desc;
69 char* end;
70 /* Start by looking for description. */
71 desc = (char*) strip(strskip(input_decoder.line_, "#"));
72 if (desc == NULL) {
73 /* Not found, fill in a default value. */
74 input_decoder.mnemonic_ = "???";
75 input_decoder.operands_ = "";
76 return;
77 }
78 /* Copy the description into the buffer, and then extract the needed parts. */
79 cstrncpy(input_decoder.buffer_, desc, kBufferSize);
80 input_decoder.mnemonic_ = input_decoder.buffer_;
81 end = (char*) strfind(input_decoder.buffer_, " ");
82 if (end == NULL) {
83 /* No operands, clean up mnemonic. */
84 rstrip(input_decoder.buffer_);
85 input_decoder.operands_ = "";
86 return;
87 }
88 /* Has mnemonic and operands. Separate out parts. */
89 *end = '\0';
90 input_decoder.operands_ = (char*) strip(end + 1);
91 rstrip(input_decoder.operands_);
92 }
93
94 /* Finds the instruction mnemonic, by looking at the end of the
95 * input line. Looks for a comment of the form '#mnemonic operands'
96 */
97 static const char* GetInstMnemonic(const NaClEnumerator* enumerator) {
98 if (input_decoder.mnemonic_ != NULL) return input_decoder.mnemonic_;
99 AssembleDesc(enumerator);
100 return input_decoder.mnemonic_;
101 }
102
103 /* Finst the instruction operands, by looking at the end of the
104 * input line. Looks for a comment of the form '#mnemonic operands'
105 */
106 static const char* GetInstOperandsText(const NaClEnumerator* enumerator) {
107 if (input_decoder.operands_ != NULL) return input_decoder.operands_;
108 AssembleDesc(enumerator);
109 return input_decoder.operands_;
110 }
111
112
113 /* Prints out the disassembled instruction. */
114 static void PrintInst(const NaClEnumerator* enumerator) {
115 size_t i;
116 const char* desc;
117 size_t num_bytes;
118 printf(" IN: %"NACL_PRIxNaClPcAddressAll": ", input_decoder.pc_address_);
119 for (i = 0; i < input_decoder.num_bytes_; ++i) {
120 printf("%02x ", enumerator->_itext[i]);
121 }
122 for (i = input_decoder.num_bytes_; i < MAX_INST_LENGTH; ++i) {
123 printf(" ");
124 }
125
126 /* Print out decoding if included on the input line. */
127 if (NULL == input_decoder.base_._get_inst_mnemonic_fn) {
128 printf("\n");
129 } else {
130 printf("%s %s\n", GetInstMnemonic(enumerator),
131 GetInstOperandsText(enumerator));
132 }
133 }
134
135 /* Returns true if the instruction parsed a legal instruction. */
136 static Bool IsInstLegal(const NaClEnumerator* enumerator) {
137 return TRUE;
138 }
139
140 static size_t InstLength(const NaClEnumerator* enumerator) {
141 return (size_t) input_decoder.num_bytes_;
142 }
143
144 static void InstallFlag(const NaClEnumerator* enumerator,
145 const char* flag_name,
146 const void* flag_address) {
147 }
148
149
150 /* Defines the registry function that creates a input decoder, and returns
151 * the decoder to be registered.
152 */
153 NaClEnumeratorDecoder* RegisterInputDecoder() {
154 input_decoder.base_._id_name = "in";
155 input_decoder.base_._legal_only = TRUE;
156 input_decoder.base_._parse_inst_fn = ParseInst;
157 input_decoder.base_._inst_length_fn = InstLength;
158 input_decoder.base_._print_inst_fn = PrintInst;
159 /* Initially assume that the input doesn't get information on
160 * mnemonic and operand text. Change (in InstallFlag) above if
161 * specified on command line.
162 */
163 input_decoder.base_._get_inst_mnemonic_fn = NULL;
164 input_decoder.base_._get_inst_num_operands_fn = NULL;
165 input_decoder.base_._get_inst_operands_text_fn = NULL;
166 input_decoder.base_._writes_to_reserved_reg_fn = NULL;
167 input_decoder.base_._is_inst_legal_fn = IsInstLegal;
168 input_decoder.base_._maybe_inst_validates_fn = NULL;
169 input_decoder.base_._segment_validates_fn = NULL;
170 input_decoder.base_._install_flag_fn = InstallFlag;
171 input_decoder.base_._usage_message = "Defines legal instructions from stdin";
172 input_decoder.num_bytes_ = 0;
173 input_decoder.line_number_ = 0;
174 input_decoder.pc_address_ = 0;
175 input_decoder.mnemonic_ = NULL;
176 input_decoder.operands_ = NULL;
177 input_decoder.configured_ = FALSE;
178 return &input_decoder.base_;
179 }
180
181 int ReadAnInstruction(InstByteArray ibytes) {
182 input_decoder.num_bytes_ = 0;
183 while (input_decoder.num_bytes_ == 0) {
184 ++input_decoder.line_number_;
185 if (fgets(input_decoder.line_, kBufferSize, stdin) == NULL) return 0;
186
187 /* If the line specifies that the input has opcode sequences plus
188 * descriptions, then install the virtuals to handle the input.
189 */
190 if (!input_decoder.configured_) {
191 if (input_decoder.line_ ==
192 strstr(input_decoder.line_, "#OPCODEPLUSDESC#")) {
193 input_decoder.base_._get_inst_mnemonic_fn = GetInstMnemonic;
194 input_decoder.base_._get_inst_operands_text_fn = GetInstOperandsText;
195 }
196 input_decoder.configured_ = TRUE;
197 }
198
199 /* If the line is a progress line, print out the corresponding progress
200 * message.
201 */
202 if (input_decoder.line_ == strstr(input_decoder.line_, "#PROGRESS#")) {
203 printf("%s", &input_decoder.line_[strlen("#PROGRESS#")]);
204 }
205
206 /* Finally, convert the input into the corresponding sequence of bytes
207 * that defines the instruction.
208 */
209 input_decoder.num_bytes_ =
210 Text2Bytes(ibytes, input_decoder.line_, "stdin",
211 input_decoder.line_number_);
212 }
213 return input_decoder.num_bytes_;
214 }
OLDNEW
« no previous file with comments | « src/trusted/validator/x86/testing/enuminsts/input_tester.h ('k') | src/trusted/validator/x86/testing/enuminsts/nacl_tester.c » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698