MCPcopy Index your code
hub / github.com/RustPython/RustPython / compile_ipow

Method compile_ipow

crates/jit/src/instructions.rs:1376–1482  ·  view source on GitHub ↗
(&mut self, a: Value, b: Value)

Source from the content-addressed store, hash-verified

1374 }
1375
1376 fn compile_ipow(&mut self, a: Value, b: Value) -> Value {
1377 let zero = self.builder.ins().iconst(types::I64, 0);
1378 let one_i64 = self.builder.ins().iconst(types::I64, 1);
1379
1380 // Create required blocks
1381 let check_negative = self.builder.create_block();
1382 let handle_negative = self.builder.create_block();
1383 let loop_block = self.builder.create_block();
1384 let continue_block = self.builder.create_block();
1385 let exit_block = self.builder.create_block();
1386
1387 // Set up block parameters
1388 self.builder.append_block_param(check_negative, types::I64); // exponent
1389 self.builder.append_block_param(check_negative, types::I64); // base
1390
1391 self.builder.append_block_param(handle_negative, types::I64); // abs(exponent)
1392 self.builder.append_block_param(handle_negative, types::I64); // base
1393
1394 self.builder.append_block_param(loop_block, types::I64); // exponent
1395 self.builder.append_block_param(loop_block, types::I64); // result
1396 self.builder.append_block_param(loop_block, types::I64); // base
1397
1398 self.builder.append_block_param(exit_block, types::I64); // final result
1399
1400 // Set up parameters for continue_block
1401 self.builder.append_block_param(continue_block, types::I64); // exponent
1402 self.builder.append_block_param(continue_block, types::I64); // result
1403 self.builder.append_block_param(continue_block, types::I64); // base
1404
1405 // Initial jump to check if exponent is negative
1406 self.builder
1407 .ins()
1408 .jump(check_negative, &[b.into(), a.into()]);
1409
1410 // Check if exponent is negative
1411 self.builder.switch_to_block(check_negative);
1412 let params = self.builder.block_params(check_negative);
1413 let exp_check = params[0];
1414 let base_check = params[1];
1415
1416 let is_negative = self
1417 .builder
1418 .ins()
1419 .icmp(IntCC::SignedLessThan, exp_check, zero);
1420 self.builder.ins().brif(
1421 is_negative,
1422 handle_negative,
1423 &[exp_check.into(), base_check.into()],
1424 loop_block,
1425 &[exp_check.into(), one_i64.into(), base_check.into()],
1426 );
1427
1428 // Handle negative exponent (return 0 for integer exponentiation)
1429 self.builder.switch_to_block(handle_negative);
1430 self.builder.ins().jump(exit_block, &[zero.into()]); // Return 0 for negative exponents
1431
1432 // Loop block logic (square-and-multiply algorithm)
1433 self.builder.switch_to_block(loop_block);

Callers 1

add_instructionMethod · 0.80

Calls 5

insMethod · 0.80
jumpMethod · 0.80
switch_to_blockMethod · 0.80
imulMethod · 0.45
selectMethod · 0.45

Tested by

no test coverage detected