예제 #1
0
    def EndEpisodeStep(self) -> random_opt_pb2.DelayedRewardStep:
        start_ms = labdate.MillisecondsTimestamp()
        step = random_opt_pb2.DelayedRewardStep(start_time_epoch_ms=start_ms, )
        try:
            clang.Compile([self.working_bytecode_path],
                          self.binary_path,
                          copts=["-O0"])
            try:
                runtimes = self.GetRuntimes()
                self.episodes[-1].binary_runtime_ms.extend(runtimes)
                if self.BinaryIsValid():
                    step.reward = self.runtime_reward(
                        sum(runtimes) / len(runtimes))
                else:
                    self.episodes[
                        -1].outcome = random_opt_pb2.DelayedRewardEpisode.EVAL_FAILED
                    step.reward = self.eval_failed_reward
            except ValueError as e:
                self.episodes[-1].outcome = random_opt_pb2.Step.EXEC_FAILED
                self.episodes[-1].outcome_error_msg = text.truncate(
                    str(e), 255)
                step.reward = self.exec_failed_reward
        except clang.ClangException as e:
            self.episodes[
                -1].outcome = random_opt_pb2.DelayedRewardEpisode.COMPILE_FAILED
            self.episodes[-1].outcome_error_msg = text.truncate(str(e), 255)
            step.reward = self.compile_failed_reward

        obs = self.observation_space.sample()
        step.total_step_runtime_ms = labdate.MillisecondsTimestamp() - start_ms
        self.episodes[-1].step.extend([step])
        return obs, step.reward, True, {}
예제 #2
0
 def reset(self):
     app.Log(2, "$ cp %s %s", self.bytecode_path,
             self.working_bytecode_path)
     shutil.copyfile(self.bytecode_path, self.working_bytecode_path)
     clang.Compile([self.working_bytecode_path],
                   self.binary_path,
                   copts=["-O0"])
     start_time = labdate.MillisecondsTimestamp()
     self.RunSetupCommand()
     self.RunBinary()
     if not self.BinaryIsValid():
         raise ValueError(f"Failed to validate base binary.")
     self.episodes.append(
         random_opt_pb2.Episode(step=[
             random_opt_pb2.Step(
                 start_time_epoch_ms=start_time,
                 status=random_opt_pb2.Step.PASS,
                 binary_runtime_ms=self.GetRuntimes(),
                 reward=0,
                 total_reward=0,
                 speedup=1.0,
                 total_speedup=1.0,
             )
         ]))
     self.episodes[-1].step[0].total_step_runtime_ms = (
         labdate.MillisecondsTimestamp() - start_time)
예제 #3
0
 def reset(self):
     """Reset the environment state."""
     app.Log(2, "$ cp %s %s", self.bytecode_path,
             self.working_bytecode_path)
     shutil.copyfile(self.bytecode_path, self.working_bytecode_path)
     clang.Compile([self.bytecode_path], self.binary_path, copts=["-O0"])
     self.RunSetupCommand()
     self.episodes.append(
         random_opt_pb2.DelayedRewardEpisode(step=[
             random_opt_pb2.DelayedRewardStep(
                 start_time_epoch_ms=labdate.MillisecondsTimestamp(), )
         ]))
예제 #4
0
def test_benchmarks(benchmark: benchmarks_pb2.Benchmark):
    """Test attributes of protos."""
    assert benchmark.name
    assert pathlib.Path(benchmark.binary).is_file()
    for path in benchmark.srcs:
        assert pathlib.Path(path).is_file()
    for path in benchmark.hdrs:
        assert pathlib.Path(path).is_file()
    # Compile the sources.
    with tempfile.TemporaryDirectory() as d:
        clang.Compile([pathlib.Path(x) for x in benchmark.srcs],
                      pathlib.Path(d) / 'exe')
        assert (pathlib.Path(d) / 'exe').is_file()
예제 #5
0
def ProduceBytecodeFromSources(
    input_paths: typing.List[pathlib.Path],
    output_path: pathlib.Path,
    copts: typing.Optional[typing.List[str]] = None,
    linkopts: typing.Optional[typing.List[str]] = None,
    timeout_seconds: int = 60,
) -> pathlib.Path:
    """Produce a single bytecode file for a set of sources.

  Args:
    input_paths: A list of input source files.
    output_path: The file to generate.
    copts: A list of additional flags to pass to clang.
    linkopts: A list of additional flags to pass to llvm-link.
    timeout_seconds: The number of seconds to allow clang to run for.

  Returns:
    The output_path.
  """
    copts = copts or []
    if output_path.is_file():
        output_path.unlink()

    # Compile each input source to a bytecode file.
    with tempfile.TemporaryDirectory() as d:
        d = pathlib.Path(d)
        input_srcs = [
            d / (crypto.sha256_str(str(src)) + ".l") for src in input_paths
        ]
        for src, input_src in zip(input_paths, input_srcs):
            clang.Compile(
                [src],
                input_src,
                copts=copts + ["-O0", "-emit-llvm", "-S", "-c"],
                timeout_seconds=timeout_seconds,
            )
        # Link the separate bytecode files.
        llvm_link.LinkBitcodeFilesToBytecode(input_srcs,
                                             output_path,
                                             linkopts,
                                             timeout_seconds=timeout_seconds)
    return output_path
예제 #6
0
    def Step(self, step: random_opt_pb2.Step) -> random_opt_pb2.Step:
        """Run a step.

    Args:
      step: A step proto with field 'opt_pass' set.

    Returns:
      The input step.
    """
        start_time = labdate.MillisecondsTimestamp()
        step.start_time_epoch_ms = start_time
        step.status = random_opt_pb2.Step.PASS
        temp_bytecode = self.working_dir / "temp_src.ll"
        temp_binary = self.working_dir / "temp_binary"

        # Run the pass.
        try:
            opt.RunOptPassOnBytecode(self.working_bytecode_path, temp_bytecode,
                                     list(step.opt_pass))
        except llvm.LlvmError as e:
            step.status = random_opt_pb2.Step.OPT_FAILED
            step.status_msg = text.truncate(str(e), 255)

        if step.status == random_opt_pb2.Step.PASS:
            # Update bytecode file.
            app.Log(2, "$ mv %s %s", temp_bytecode, self.working_bytecode_path)
            step.bytecode_changed = BytecodesAreEqual(
                temp_bytecode, self.working_bytecode_path)
            os.rename(str(temp_bytecode), str(self.working_bytecode_path))
            # Compile a new binary.
            try:
                clang.Compile([self.working_bytecode_path],
                              temp_binary,
                              copts=["-O0"])
                step.binary_changed = BinariesAreEqual(temp_binary,
                                                       self.binary_path)
                os.rename(str(temp_binary), str(self.binary_path))
            except llvm.LlvmError as e:
                step.status = random_opt_pb2.Step.COMPILE_FAILED
                step.status_msg = text.truncate(str(e), 255)

        if step.status == random_opt_pb2.Step.PASS:
            # Get the binary runtime.
            try:
                step.binary_runtime_ms.extend(self.GetRuntimes())
            except ValueError as e:
                step.status = random_opt_pb2.Step.EXEC_FAILED
                step.status_msg = text.truncate(str(e), 255)

        if step.status == random_opt_pb2.Step.PASS:
            if self.BinaryIsValid():
                step.speedup = (
                    sum(self.episodes[-1].step[-1].binary_runtime_ms) /
                    len(self.episodes[-1].step[-1].binary_runtime_ms)) / (sum(
                        step.binary_runtime_ms) / len(step.binary_runtime_ms))
                step.total_speedup = (
                    sum(self.episodes[-1].step[0].binary_runtime_ms) /
                    len(self.episodes[-1].step[0].binary_runtime_ms)) / (sum(
                        step.binary_runtime_ms) / len(step.binary_runtime_ms))
            else:
                step.status = random_opt_pb2.Step.EVAL_FAILED

        step.reward = self.Reward(step.status, step.speedup)
        step.total_reward = self.episodes[-1].step[
            -1].total_reward + step.reward
        step.total_step_runtime_ms = labdate.MillisecondsTimestamp(
        ) - start_time
        return step