#ifndef SYNTH_LIBCLANG_HPP_INCLUDED
#define SYNTH_LIBCLANG_HPP_INCLUDED
#include <clang-c/CXString.h>
#include <cassert>
#include <ostream>
#include <string>
namespace synth {
class CgStr {
public:
CgStr(CXString&& s)
: m_data(s)
{ }
CgStr(CgStr&& other)
: m_data(std::move(other.m_data))
{
other.m_data.data = nullptr;
}
CgStr& operator=(CgStr&& other) {
destroy();
m_data = std::move(other.m_data);
other.m_data.data = nullptr; // HACK Undocumented behavior.
assert(!other.valid());
return *this;
}
~CgStr() {
destroy();
}
char const* get() const { return clang_getCString(m_data); }
char const* gets() const
{
auto s = get();
return s ? s : "";
}
std::string copy() const
{
auto s = get();
return s ? s : std::string();
}
bool valid() const { return m_data.data != nullptr; } // HACK
bool empty() const
{
if (!valid())
return true;
auto s = get();
return !s || !*s;
}
private:
void destroy() { if (valid()) clang_disposeString(m_data); }
CXString m_data;
};
inline std::ostream& operator<< (std::ostream& out, CgStr const& s)
{
return out << s.gets();
}
} // namespace synth
#endif