Checks that the input operands actually match the given format.
(inst_name: &str, operands_in: &[Operand], format: &InstructionFormat)
| 298 | |
| 299 | /// Checks that the input operands actually match the given format. |
| 300 | fn verify_format(inst_name: &str, operands_in: &[Operand], format: &InstructionFormat) { |
| 301 | // A format is defined by: |
| 302 | // - its number of input value operands, |
| 303 | // - its number and names of input immediate operands, |
| 304 | // - whether it has a value list or not. |
| 305 | let mut num_values = 0; |
| 306 | let mut num_blocks = 0; |
| 307 | let mut num_raw_blocks = 0; |
| 308 | let mut num_immediates = 0; |
| 309 | |
| 310 | for operand in operands_in.iter() { |
| 311 | if operand.is_varargs() { |
| 312 | assert!( |
| 313 | format.has_value_list, |
| 314 | "instruction {} has varargs, but its format {} doesn't have a value list; you may \ |
| 315 | need to use a different format.", |
| 316 | inst_name, format.name |
| 317 | ); |
| 318 | } |
| 319 | if operand.is_value() { |
| 320 | num_values += 1; |
| 321 | } |
| 322 | if operand.kind.is_block() { |
| 323 | num_blocks += 1; |
| 324 | } else if operand.kind.is_raw_block() { |
| 325 | num_raw_blocks += 1; |
| 326 | } else if operand.is_immediate_or_entityref() { |
| 327 | if let Some(format_field) = format.imm_fields.get(num_immediates) { |
| 328 | assert_eq!( |
| 329 | format_field.kind.rust_field_name, |
| 330 | operand.kind.rust_field_name, |
| 331 | "{}th operand of {} should be {} (according to format), not {} (according to \ |
| 332 | inst definition). You may need to use a different format.", |
| 333 | num_immediates, |
| 334 | inst_name, |
| 335 | format_field.kind.rust_field_name, |
| 336 | operand.kind.rust_field_name |
| 337 | ); |
| 338 | num_immediates += 1; |
| 339 | } |
| 340 | } |
| 341 | } |
| 342 | |
| 343 | assert_eq!( |
| 344 | num_values, format.num_value_operands, |
| 345 | "inst {} doesn't have as many value input operands as its format {} declares; you may need \ |
| 346 | to use a different format.", |
| 347 | inst_name, format.name |
| 348 | ); |
| 349 | |
| 350 | assert_eq!( |
| 351 | num_blocks, format.num_block_operands, |
| 352 | "inst {} doesn't have as many block input operands as its format {} declares; you may need \ |
| 353 | to use a different format.", |
| 354 | inst_name, format.name, |
| 355 | ); |
| 356 | |
| 357 | assert_eq!( |
no test coverage detected