// This file is autogenerated by generate_proto_header.py, do not edit

#ifndef NINJA_FRONTEND_PB_H
#define NINJA_FRONTEND_PB_H

#include <inttypes.h>

#include <iostream>
#include <string>
#include <vector>

#include "proto.h"

namespace ninja {
struct Status {
  struct TotalEdges {
    uint32_t total_edges_;
    bool has_total_edges_;

    TotalEdges() {
      has_total_edges_ = false;
      total_edges_ = static_cast< uint32_t >(0);
    }

    TotalEdges(const TotalEdges&);
    void operator=(const TotalEdges&);

    void SerializeToOstream(std::ostream* output__) const {
      WriteVarint32(output__, 1, total_edges_);
    }

    size_t ByteSizeLong() const {
      size_t size = 0;
      size += VarintSize32(total_edges_) + 1;
      return size;
    }

    void Clear() {
      total_edges_ = static_cast< uint32_t >(0);
    }

    uint32_t* mutable_total_edges() {
      has_total_edges_ = true;
      return &total_edges_;
    }
    void set_total_edges(const uint32_t& value) {
      has_total_edges_ = true;
      total_edges_ = value;
    }
  };

  struct BuildStarted {
    uint32_t parallelism_;
    bool has_parallelism_;
    bool verbose_;
    bool has_verbose_;

    BuildStarted() {
      has_parallelism_ = false;
      parallelism_ = static_cast< uint32_t >(0);
      has_verbose_ = false;
      verbose_ = static_cast< bool >(0);
    }

    BuildStarted(const BuildStarted&);
    void operator=(const BuildStarted&);

    void SerializeToOstream(std::ostream* output__) const {
      WriteVarint32(output__, 1, parallelism_);
      WriteVarint32(output__, 2, verbose_);
    }

    size_t ByteSizeLong() const {
      size_t size = 0;
      size += VarintSize32(parallelism_) + 1;
      size += VarintSizeBool(verbose_) + 1;
      return size;
    }

    void Clear() {
      parallelism_ = static_cast< uint32_t >(0);
      verbose_ = static_cast< bool >(0);
    }

    uint32_t* mutable_parallelism() {
      has_parallelism_ = true;
      return &parallelism_;
    }
    void set_parallelism(const uint32_t& value) {
      has_parallelism_ = true;
      parallelism_ = value;
    }
    bool* mutable_verbose() {
      has_verbose_ = true;
      return &verbose_;
    }
    void set_verbose(const bool& value) {
      has_verbose_ = true;
      verbose_ = value;
    }
  };

  struct BuildFinished {
    BuildFinished() {
    }

    BuildFinished(const BuildFinished&);
    void operator=(const BuildFinished&);

    void SerializeToOstream(std::ostream* output__) const {
    }

    size_t ByteSizeLong() const {
      size_t size = 0;
      return size;
    }

    void Clear() {
    }

  };

  struct EdgeStarted {
    uint32_t id_;
    bool has_id_;
    uint32_t start_time_;
    bool has_start_time_;
    std::vector< std::string > inputs_;
    bool has_inputs_;
    std::vector< std::string > outputs_;
    bool has_outputs_;
    std::string desc_;
    bool has_desc_;
    std::string command_;
    bool has_command_;
    bool console_;
    bool has_console_;

    EdgeStarted() {
      has_id_ = false;
      id_ = static_cast< uint32_t >(0);
      has_start_time_ = false;
      start_time_ = static_cast< uint32_t >(0);
      has_inputs_ = false;
      has_outputs_ = false;
      has_desc_ = false;
      has_command_ = false;
      has_console_ = false;
      console_ = static_cast< bool >(0);
    }

    EdgeStarted(const EdgeStarted&);
    void operator=(const EdgeStarted&);

    void SerializeToOstream(std::ostream* output__) const {
      WriteVarint32(output__, 1, id_);
      WriteVarint32(output__, 2, start_time_);
      for (std::vector< std::string >::const_iterator it_ = inputs_.begin();
          it_ != inputs_.end(); it_++) {
        WriteString(output__, 3, *it_);
      }
      for (std::vector< std::string >::const_iterator it_ = outputs_.begin();
          it_ != outputs_.end(); it_++) {
        WriteString(output__, 4, *it_);
      }
      WriteString(output__, 5, desc_);
      WriteString(output__, 6, command_);
      WriteVarint32(output__, 7, console_);
    }

    size_t ByteSizeLong() const {
      size_t size = 0;
      size += VarintSize32(id_) + 1;
      size += VarintSize32(start_time_) + 1;
      for (std::vector< std::string >::const_iterator it_ = inputs_.begin();
          it_ != inputs_.end(); it_++) {
        size += StringSize(*it_) + 1;
      }
      for (std::vector< std::string >::const_iterator it_ = outputs_.begin();
          it_ != outputs_.end(); it_++) {
        size += StringSize(*it_) + 1;
      }
      size += StringSize(desc_) + 1;
      size += StringSize(command_) + 1;
      size += VarintSizeBool(console_) + 1;
      return size;
    }

    void Clear() {
      id_ = static_cast< uint32_t >(0);
      start_time_ = static_cast< uint32_t >(0);
      inputs_.clear();
      outputs_.clear();
      desc_.clear();
      command_.clear();
      console_ = static_cast< bool >(0);
    }

    uint32_t* mutable_id() {
      has_id_ = true;
      return &id_;
    }
    void set_id(const uint32_t& value) {
      has_id_ = true;
      id_ = value;
    }
    uint32_t* mutable_start_time() {
      has_start_time_ = true;
      return &start_time_;
    }
    void set_start_time(const uint32_t& value) {
      has_start_time_ = true;
      start_time_ = value;
    }
    std::vector< std::string >* mutable_inputs() {
      has_inputs_ = true;
      return &inputs_;
    }
    void add_inputs(const std::string& value) {
      has_inputs_ = true;
      inputs_.push_back(value);
    }
    void set_inputs(const std::vector< std::string >& value) {
      has_inputs_ = true;
      inputs_ = value;
    }
    std::vector< std::string >* mutable_outputs() {
      has_outputs_ = true;
      return &outputs_;
    }
    void add_outputs(const std::string& value) {
      has_outputs_ = true;
      outputs_.push_back(value);
    }
    void set_outputs(const std::vector< std::string >& value) {
      has_outputs_ = true;
      outputs_ = value;
    }
    std::string* mutable_desc() {
      has_desc_ = true;
      return &desc_;
    }
    void set_desc(const std::string& value) {
      has_desc_ = true;
      desc_ = value;
    }
    std::string* mutable_command() {
      has_command_ = true;
      return &command_;
    }
    void set_command(const std::string& value) {
      has_command_ = true;
      command_ = value;
    }
    bool* mutable_console() {
      has_console_ = true;
      return &console_;
    }
    void set_console(const bool& value) {
      has_console_ = true;
      console_ = value;
    }
  };

  struct EdgeFinished {
    uint32_t id_;
    bool has_id_;
    uint32_t end_time_;
    bool has_end_time_;
    int32_t status_;
    bool has_status_;
    std::string output_;
    bool has_output_;
    uint32_t user_time_;
    bool has_user_time_;
    uint32_t system_time_;
    bool has_system_time_;

    EdgeFinished() {
      has_id_ = false;
      id_ = static_cast< uint32_t >(0);
      has_end_time_ = false;
      end_time_ = static_cast< uint32_t >(0);
      has_status_ = false;
      status_ = static_cast< int32_t >(0);
      has_output_ = false;
      has_user_time_ = false;
      user_time_ = static_cast< uint32_t >(0);
      has_system_time_ = false;
      system_time_ = static_cast< uint32_t >(0);
    }

    EdgeFinished(const EdgeFinished&);
    void operator=(const EdgeFinished&);

    void SerializeToOstream(std::ostream* output__) const {
      WriteVarint32(output__, 1, id_);
      WriteVarint32(output__, 2, end_time_);
      WriteVarint32(output__, 3, ZigZagEncode32(status_));
      WriteString(output__, 4, output_);
      WriteVarint32(output__, 5, user_time_);
      WriteVarint32(output__, 6, system_time_);
    }

    size_t ByteSizeLong() const {
      size_t size = 0;
      size += VarintSize32(id_) + 1;
      size += VarintSize32(end_time_) + 1;
      size += VarintSize32(ZigZagEncode32(status_)) + 1;
      size += StringSize(output_) + 1;
      size += VarintSize32(user_time_) + 1;
      size += VarintSize32(system_time_) + 1;
      return size;
    }

    void Clear() {
      id_ = static_cast< uint32_t >(0);
      end_time_ = static_cast< uint32_t >(0);
      status_ = static_cast< int32_t >(0);
      output_.clear();
      user_time_ = static_cast< uint32_t >(0);
      system_time_ = static_cast< uint32_t >(0);
    }

    uint32_t* mutable_id() {
      has_id_ = true;
      return &id_;
    }
    void set_id(const uint32_t& value) {
      has_id_ = true;
      id_ = value;
    }
    uint32_t* mutable_end_time() {
      has_end_time_ = true;
      return &end_time_;
    }
    void set_end_time(const uint32_t& value) {
      has_end_time_ = true;
      end_time_ = value;
    }
    int32_t* mutable_status() {
      has_status_ = true;
      return &status_;
    }
    void set_status(const int32_t& value) {
      has_status_ = true;
      status_ = value;
    }
    std::string* mutable_output() {
      has_output_ = true;
      return &output_;
    }
    void set_output(const std::string& value) {
      has_output_ = true;
      output_ = value;
    }
    uint32_t* mutable_user_time() {
      has_user_time_ = true;
      return &user_time_;
    }
    void set_user_time(const uint32_t& value) {
      has_user_time_ = true;
      user_time_ = value;
    }
    uint32_t* mutable_system_time() {
      has_system_time_ = true;
      return &system_time_;
    }
    void set_system_time(const uint32_t& value) {
      has_system_time_ = true;
      system_time_ = value;
    }
  };

  struct Message {
    enum Level {
      INFO = 0,
      WARNING = 1,
      ERROR = 2,
      DEBUG = 3,
    };

    ::ninja::Status::Message::Level level_;
    bool has_level_;
    std::string message_;
    bool has_message_;

    Message() {
      has_level_ = false;
      level_ = static_cast< ::ninja::Status::Message::Level >(0);
      has_message_ = false;
    }

    Message(const Message&);
    void operator=(const Message&);

    void SerializeToOstream(std::ostream* output__) const {
      WriteVarint32SignExtended(output__, 1, static_cast<int32_t>(level_));
      WriteString(output__, 2, message_);
    }

    size_t ByteSizeLong() const {
      size_t size = 0;
      size += VarintSize32SignExtended(static_cast<int32_t>(level_)) + 1;
      size += StringSize(message_) + 1;
      return size;
    }

    void Clear() {
      level_ = static_cast< ::ninja::Status::Message::Level >(0);
      message_.clear();
    }

    ::ninja::Status::Message::Level* mutable_level() {
      has_level_ = true;
      return &level_;
    }
    void set_level(const ::ninja::Status::Message::Level& value) {
      has_level_ = true;
      level_ = value;
    }
    std::string* mutable_message() {
      has_message_ = true;
      return &message_;
    }
    void set_message(const std::string& value) {
      has_message_ = true;
      message_ = value;
    }
  };

  ::ninja::Status::TotalEdges total_edges_;
  bool has_total_edges_;
  ::ninja::Status::BuildStarted build_started_;
  bool has_build_started_;
  ::ninja::Status::BuildFinished build_finished_;
  bool has_build_finished_;
  ::ninja::Status::EdgeStarted edge_started_;
  bool has_edge_started_;
  ::ninja::Status::EdgeFinished edge_finished_;
  bool has_edge_finished_;
  ::ninja::Status::Message message_;
  bool has_message_;

  Status() {
    has_total_edges_ = false;
    has_build_started_ = false;
    has_build_finished_ = false;
    has_edge_started_ = false;
    has_edge_finished_ = false;
    has_message_ = false;
  }

  Status(const Status&);
  void operator=(const Status&);

  void SerializeToOstream(std::ostream* output__) const {
    if (has_total_edges_) {
      WriteLengthDelimited(output__, 1,
                           total_edges_.ByteSizeLong());
      total_edges_.SerializeToOstream(output__);
    }
    if (has_build_started_) {
      WriteLengthDelimited(output__, 2,
                           build_started_.ByteSizeLong());
      build_started_.SerializeToOstream(output__);
    }
    if (has_build_finished_) {
      WriteLengthDelimited(output__, 3,
                           build_finished_.ByteSizeLong());
      build_finished_.SerializeToOstream(output__);
    }
    if (has_edge_started_) {
      WriteLengthDelimited(output__, 4,
                           edge_started_.ByteSizeLong());
      edge_started_.SerializeToOstream(output__);
    }
    if (has_edge_finished_) {
      WriteLengthDelimited(output__, 5,
                           edge_finished_.ByteSizeLong());
      edge_finished_.SerializeToOstream(output__);
    }
    if (has_message_) {
      WriteLengthDelimited(output__, 6,
                           message_.ByteSizeLong());
      message_.SerializeToOstream(output__);
    }
  }

  size_t ByteSizeLong() const {
    size_t size = 0;
    if (has_total_edges_) {
      size += 1 + VarintSize32(total_edges_.ByteSizeLong());
      size += total_edges_.ByteSizeLong();
    }
    if (has_build_started_) {
      size += 1 + VarintSize32(build_started_.ByteSizeLong());
      size += build_started_.ByteSizeLong();
    }
    if (has_build_finished_) {
      size += 1 + VarintSize32(build_finished_.ByteSizeLong());
      size += build_finished_.ByteSizeLong();
    }
    if (has_edge_started_) {
      size += 1 + VarintSize32(edge_started_.ByteSizeLong());
      size += edge_started_.ByteSizeLong();
    }
    if (has_edge_finished_) {
      size += 1 + VarintSize32(edge_finished_.ByteSizeLong());
      size += edge_finished_.ByteSizeLong();
    }
    if (has_message_) {
      size += 1 + VarintSize32(message_.ByteSizeLong());
      size += message_.ByteSizeLong();
    }
    return size;
  }

  void Clear() {
    if (has_total_edges_) {
      total_edges_.Clear();
      has_total_edges_ = false;
    }
    if (has_build_started_) {
      build_started_.Clear();
      has_build_started_ = false;
    }
    if (has_build_finished_) {
      build_finished_.Clear();
      has_build_finished_ = false;
    }
    if (has_edge_started_) {
      edge_started_.Clear();
      has_edge_started_ = false;
    }
    if (has_edge_finished_) {
      edge_finished_.Clear();
      has_edge_finished_ = false;
    }
    if (has_message_) {
      message_.Clear();
      has_message_ = false;
    }
  }

  ::ninja::Status::TotalEdges* mutable_total_edges() {
    has_total_edges_ = true;
    return &total_edges_;
  }
  ::ninja::Status::BuildStarted* mutable_build_started() {
    has_build_started_ = true;
    return &build_started_;
  }
  ::ninja::Status::BuildFinished* mutable_build_finished() {
    has_build_finished_ = true;
    return &build_finished_;
  }
  ::ninja::Status::EdgeStarted* mutable_edge_started() {
    has_edge_started_ = true;
    return &edge_started_;
  }
  ::ninja::Status::EdgeFinished* mutable_edge_finished() {
    has_edge_finished_ = true;
    return &edge_finished_;
  }
  ::ninja::Status::Message* mutable_message() {
    has_message_ = true;
    return &message_;
  }
};

}
#endif // NINJA_FRONTEND_PB_H
