code: def register_ir_function(
      self,
      name: str,
      type_parameters: Union[Tuple[HailType, ...], List[HailType]],
      value_parameter_names: Union[Tuple[str, ...], List[str]],
      value_parameter_types: Union[
          Tuple[HailType, ...], List[HailType]
      ],
      return_type: HailType,
      body: Expression,
  ):
      r = CSERenderer()
      code = r(finalize_randomness(body._ir))
      jbody = self._parse_value_ir(
          code,
          ref_map=dict(
              zip(value_parameter_names, value_parameter_types)
          ),
      )
      self._registered_ir_function_names.add(name)
  
      self.hail_package().expr.ir.functions.IRFunctionRegistry.pyRegisterIR(
          name,
          [ta._parsable_string() for ta in type_parameters],
          value_parameter_names,
          [pt._parsable_string() for pt in value_parameter_types],
          return_type._parsable_string(),
          jbody,
      )
  
imports: from typing import Optional, Union, Tuple, List
  import os
  import sys
  from py4j.java_gateway import JavaGateway, GatewayParameters, launch_gateway
  from hail.ir.renderer import CSERenderer
  from hail.ir import finalize_randomness
  from .py4j_backend import Py4JBackend, uninstall_exception_handler
  from .backend import local_jar_information
  from ..expr import Expression
  from ..expr.types import HailType
  from hailtop.utils import find_spark_home
  from hailtop.fs.router_fs import RouterFS
  from hailtop.aiotools.validators import validate_file
label_desc: Use image node_id 3 for calling the LocalBackend obj's underlying member method code with example usage: obj.register_ir_function(name, type_parameters, value_parameter_names, value_parameter_types, return_type, body) without return types