// Copyright (C) 2010, Guy Barrand. All rights reserved.
// See the file tools.license for terms.

#ifndef tools_wroot_free_seg
#define tools_wroot_free_seg

#include "seek"
#include "wbuf"

#include <ostream>

namespace tools {
namespace wroot {

class free_seg {
  static uint32 START_BIG_FILE() {return 2000000000;}
public:
  free_seg(std::ostream& a_out,seek a_first,seek a_last)
  :m_out(a_out),m_first(a_first),m_last(a_last){}
  virtual ~free_seg(){}
public:
  free_seg(const free_seg& a_from)
  :m_out(a_from.m_out),m_first(a_from.m_first),m_last(a_from.m_last)
  {}
  free_seg& operator=(const free_seg& a_from){
    m_first = a_from.m_first;
    m_last = a_from.m_last;
    return *this;
  }
public:
  seek first() const {return m_first;}
  seek last() const {return m_last;}

  unsigned int record_size() const {
    //GB if(fLast>RIO_START_BIG_FILE) {
    if((m_first>START_BIG_FILE())|| //GB
       (m_last>START_BIG_FILE()) ){
      return sizeof(short) +  2 * sizeof(seek);
    } else {
      return sizeof(short) +  2 * sizeof(seek32);
    }
  }

  bool fill_buffer(wbuf& a_wb) {
    short version = 1;

    //GB if(fLast>START_BIG_FILE()) version += 1000;
    if((m_first>START_BIG_FILE())||
       (m_last>START_BIG_FILE())) version += 1000;

    if(!a_wb.write(version)) return false;

    if(version>1000) {
      if(!a_wb.write(m_first)) return false;
      if(!a_wb.write(m_last)) return false;
    } else {
      if(m_first>START_BIG_FILE()) { //GB
        m_out << "tools::wroot::free_seg::fill_buffer :"
             << " attempt to write big Seek "
             << m_first << " on 32 bits."
             << std::endl;
        return false;
      }
      if(!a_wb.write((seek32)m_first)) return false;
      if(m_last>START_BIG_FILE()) { //GB
        m_out << "tools::wroot::free_seg::fill_buffer :"
             << " attempt to write big seek "
             << m_last << " on 32 bits."
             << std::endl;
        return false;
      }
      if(!a_wb.write((seek32)m_last)) return false;
    }

    return true;
  }

protected:
  std::ostream& m_out;
  seek m_first;  //First free word of segment
  seek m_last;   //Last free word of segment
};

}}

#endif
