diff --git a/AK/LogStream.cpp b/AK/LogStream.cpp index e2a49cc076..dac64adfe1 100644 --- a/AK/LogStream.cpp +++ b/AK/LogStream.cpp @@ -34,6 +34,10 @@ # include #endif +#if !defined(KERNEL) && !defined(BOOTSTRAPPER) +#include +#endif + namespace AK { const LogStream& operator<<(const LogStream& stream, const String& value) @@ -163,4 +167,20 @@ DebugLogStream::~DebugLogStream() write(&newline, 1); } +#if !defined(KERNEL) && !defined(BOOTSTRAPPER) +StdLogStream::~StdLogStream() +{ + char newline = '\n'; + write(&newline, 1); +} + +void StdLogStream::write(const char* characters, int length) const +{ + if (::write(m_fd, characters, length) < 0) { + perror("StdLogStream::write"); + ASSERT_NOT_REACHED(); + } +} +#endif + } diff --git a/AK/LogStream.h b/AK/LogStream.h index b7345564b5..8b142193c5 100644 --- a/AK/LogStream.h +++ b/AK/LogStream.h @@ -68,6 +68,24 @@ public: } }; +#if !defined(KERNEL) && !defined(BOOTSTRAPPER) +class StdLogStream final : public LogStream { +public: + StdLogStream(int fd) + : m_fd(fd) + { + } + virtual ~StdLogStream() override; + virtual void write(const char* characters, int length) const override; + +private: + int m_fd { -1 }; +}; + +inline StdLogStream out() { return StdLogStream(STDOUT_FILENO); } +inline StdLogStream warn() { return StdLogStream(STDERR_FILENO); } +#endif + #if !defined(BOOTSTRAPPER) && defined(KERNEL) class KernelLogStream final : public LogStream { public: @@ -128,3 +146,8 @@ DebugLogStream klog(); using AK::dbg; using AK::klog; using AK::LogStream; + +#if !defined(KERNEL) && !defined(BOOTSTRAPPER) +using AK::out; +using AK::warn; +#endif diff --git a/DevTools/FormCompiler/main.cpp b/DevTools/FormCompiler/main.cpp index 0823dbe46c..0ccafa31ce 100644 --- a/DevTools/FormCompiler/main.cpp +++ b/DevTools/FormCompiler/main.cpp @@ -61,7 +61,7 @@ int main(int argc, char** argv) return 1; } - dbg() << "#pragma once"; + out() << "#pragma once"; widgets.as_array().for_each([&](auto& value) { const JsonObject& widget_object = value.as_object(); @@ -69,36 +69,36 @@ int main(int argc, char** argv) StringBuilder builder; auto parts = class_name.split(':'); builder.append(parts.last()); - dbg() << "#include "; + out() << "#include "; }); - dbg() << "struct UI_" << name << " {"; - dbg() << " RefPtr main_widget;"; + out() << "struct UI_" << name << " {"; + out() << " RefPtr main_widget;"; widgets.as_array().for_each([&](auto& value) { ASSERT(value.is_object()); const JsonObject& widget_object = value.as_object(); auto name = widget_object.get("name").to_string(); auto class_name = widget_object.get("class").to_string(); - dbg() << " RefPtr<" << class_name << "> " << name << ";"; + out() << " RefPtr<" << class_name << "> " << name << ";"; }); - dbg() << " UI_" << name << "();"; + out() << " UI_" << name << "();"; - dbg() << "};"; + out() << "};"; - dbg() << "UI_" << name << "::UI_" << name << "()"; - dbg() << "{"; + out() << "UI_" << name << "::UI_" << name << "()"; + out() << "{"; - dbg() << " main_widget = GUI::Widget::construct();"; - dbg() << " main_widget->set_fill_with_background_color(true);"; + out() << " main_widget = GUI::Widget::construct();"; + out() << " main_widget->set_fill_with_background_color(true);"; widgets.as_array().for_each([&](auto& value) { ASSERT(value.is_object()); const JsonObject& widget_object = value.as_object(); auto name = widget_object.get("name").to_string(); auto class_name = widget_object.get("class").to_string(); - dbg() << " " << name << " = main_widget->add<" << class_name << ">();"; + out() << " " << name << " = main_widget->add<" << class_name << ">();"; widget_object.for_each_member([&](auto& property_name, const JsonValue& property_value) { if (property_name == "class") @@ -111,12 +111,12 @@ int main(int argc, char** argv) else value = property_value.serialized(); - dbg() << " " << name << "->set_" << property_name << "(" << value << ");"; + out() << " " << name << "->set_" << property_name << "(" << value << ");"; }); - dbg() << ""; + out() << ""; }); - dbg() << "}"; + out() << "}"; return 0; } diff --git a/DevTools/IPCCompiler/main.cpp b/DevTools/IPCCompiler/main.cpp index 252ef7dd4e..4766850840 100644 --- a/DevTools/IPCCompiler/main.cpp +++ b/DevTools/IPCCompiler/main.cpp @@ -100,7 +100,7 @@ int main(int argc, char** argv) auto consume_specific = [&](char ch) { if (peek() != ch) { - dbg() << "consume_specific: wanted '" << ch << "', but got '" << peek() << "' at index " << index; + warn() << "consume_specific: wanted '" << ch << "', but got '" << peek() << "' at index " << index; } ASSERT(peek() == ch); ++index; @@ -223,36 +223,36 @@ int main(int argc, char** argv) while (index < file_contents.size()) parse_endpoint(); - dbg() << "#pragma once"; - dbg() << "#include "; - dbg() << "#include "; - dbg() << "#include "; - dbg() << "#include "; - dbg() << "#include "; - dbg() << "#include "; - dbg() << "#include "; - dbg() << "#include "; - dbg() << "#include "; - dbg(); + out() << "#pragma once"; + out() << "#include "; + out() << "#include "; + out() << "#include "; + out() << "#include "; + out() << "#include "; + out() << "#include "; + out() << "#include "; + out() << "#include "; + out() << "#include "; + out(); for (auto& endpoint : endpoints) { - dbg() << "namespace Messages {"; - dbg() << "namespace " << endpoint.name << " {"; - dbg(); + out() << "namespace Messages {"; + out() << "namespace " << endpoint.name << " {"; + out(); HashMap message_ids; - dbg() << "enum class MessageID : i32 {"; + out() << "enum class MessageID : i32 {"; for (auto& message : endpoint.messages) { message_ids.set(message.name, message_ids.size() + 1); - dbg() << " " << message.name << " = " << message_ids.size() << ","; + out() << " " << message.name << " = " << message_ids.size() << ","; if (message.is_synchronous) { message_ids.set(message.response_name(), message_ids.size() + 1); - dbg() << " " << message.response_name() << " = " << message_ids.size() << ","; + out() << " " << message.response_name() << " = " << message_ids.size() << ","; } } - dbg() << "};"; - dbg(); + out() << "};"; + out(); auto constructor_for_message = [&](const String& name, const Vector& parameters) { StringBuilder builder; @@ -289,39 +289,39 @@ int main(int argc, char** argv) }; auto do_message = [&](const String& name, const Vector& parameters, const String& response_type = {}) { - dbg() << "class " << name << " final : public IPC::Message {"; - dbg() << "public:"; + out() << "class " << name << " final : public IPC::Message {"; + out() << "public:"; if (!response_type.is_null()) - dbg() << " typedef class " << response_type << " ResponseType;"; - dbg() << " " << constructor_for_message(name, parameters); - dbg() << " virtual ~" << name << "() override {}"; - dbg() << " virtual i32 endpoint_magic() const override { return " << endpoint.magic << "; }"; - dbg() << " virtual i32 message_id() const override { return (int)MessageID::" << name << "; }"; - dbg() << " static i32 static_message_id() { return (int)MessageID::" << name << "; }"; - dbg() << " virtual const char* message_name() const override { return \"" << endpoint.name << "::" << name << "\"; }"; - dbg() << " static OwnPtr<" << name << "> decode(BufferStream& stream, size_t& size_in_bytes)"; - dbg() << " {"; + out() << " typedef class " << response_type << " ResponseType;"; + out() << " " << constructor_for_message(name, parameters); + out() << " virtual ~" << name << "() override {}"; + out() << " virtual i32 endpoint_magic() const override { return " << endpoint.magic << "; }"; + out() << " virtual i32 message_id() const override { return (int)MessageID::" << name << "; }"; + out() << " static i32 static_message_id() { return (int)MessageID::" << name << "; }"; + out() << " virtual const char* message_name() const override { return \"" << endpoint.name << "::" << name << "\"; }"; + out() << " static OwnPtr<" << name << "> decode(BufferStream& stream, size_t& size_in_bytes)"; + out() << " {"; - dbg() << " IPC::Decoder decoder(stream);"; + out() << " IPC::Decoder decoder(stream);"; for (auto& parameter : parameters) { String initial_value = "{}"; if (parameter.type == "bool") initial_value = "false"; - dbg() << " " << parameter.type << " " << parameter.name << " = " << initial_value << ";"; + out() << " " << parameter.type << " " << parameter.name << " = " << initial_value << ";"; if (parameter.type == "Vector") { - dbg() << " u64 " << parameter.name << "_size = 0;"; - dbg() << " stream >> " << parameter.name << "_size;"; - dbg() << " for (size_t i = 0; i < " << parameter.name << "_size; ++i) {"; - dbg() << " Gfx::Rect rect;"; - dbg() << " if (!decoder.decode(rect))"; - dbg() << " return nullptr;"; - dbg() << " " << parameter.name << ".append(move(rect));"; - dbg() << " }"; + out() << " u64 " << parameter.name << "_size = 0;"; + out() << " stream >> " << parameter.name << "_size;"; + out() << " for (size_t i = 0; i < " << parameter.name << "_size; ++i) {"; + out() << " Gfx::Rect rect;"; + out() << " if (!decoder.decode(rect))"; + out() << " return nullptr;"; + out() << " " << parameter.name << ".append(move(rect));"; + out() << " }"; } else { - dbg() << " if (!decoder.decode(" << parameter.name << "))"; - dbg() << " return nullptr;"; + out() << " if (!decoder.decode(" << parameter.name << "))"; + out() << " return nullptr;"; } } @@ -332,56 +332,56 @@ int main(int argc, char** argv) if (i != parameters.size() - 1) builder.append(", "); } - dbg() << " size_in_bytes = stream.offset();"; - dbg() << " return make<" << name << ">(" << builder.to_string() << ");"; - dbg() << " }"; - dbg() << " virtual IPC::MessageBuffer encode() const override"; - dbg() << " {"; - dbg() << " IPC::MessageBuffer buffer;"; - dbg() << " IPC::Encoder stream(buffer);"; - dbg() << " stream << endpoint_magic();"; - dbg() << " stream << (int)MessageID::" << name << ";"; + out() << " size_in_bytes = stream.offset();"; + out() << " return make<" << name << ">(" << builder.to_string() << ");"; + out() << " }"; + out() << " virtual IPC::MessageBuffer encode() const override"; + out() << " {"; + out() << " IPC::MessageBuffer buffer;"; + out() << " IPC::Encoder stream(buffer);"; + out() << " stream << endpoint_magic();"; + out() << " stream << (int)MessageID::" << name << ";"; for (auto& parameter : parameters) { if (parameter.type == "Gfx::Color") { - dbg() << " stream << m_" << parameter.name << ".value();"; + out() << " stream << m_" << parameter.name << ".value();"; } else if (parameter.type == "Gfx::Size") { - dbg() << " stream << m_" << parameter.name << ".width();"; - dbg() << " stream << m_" << parameter.name << ".height();"; + out() << " stream << m_" << parameter.name << ".width();"; + out() << " stream << m_" << parameter.name << ".height();"; } else if (parameter.type == "Gfx::Point") { - dbg() << " stream << m_" << parameter.name << ".x();"; - dbg() << " stream << m_" << parameter.name << ".y();"; + out() << " stream << m_" << parameter.name << ".x();"; + out() << " stream << m_" << parameter.name << ".y();"; } else if (parameter.type == "Gfx::Rect") { - dbg() << " stream << m_" << parameter.name << ".x();"; - dbg() << " stream << m_" << parameter.name << ".y();"; - dbg() << " stream << m_" << parameter.name << ".width();"; - dbg() << " stream << m_" << parameter.name << ".height();"; + out() << " stream << m_" << parameter.name << ".x();"; + out() << " stream << m_" << parameter.name << ".y();"; + out() << " stream << m_" << parameter.name << ".width();"; + out() << " stream << m_" << parameter.name << ".height();"; } else if (parameter.type == "Vector") { - dbg() << " stream << (u64)m_" << parameter.name << ".size();"; - dbg() << " for (auto& rect : m_" << parameter.name << ") {"; - dbg() << " stream << rect.x();"; - dbg() << " stream << rect.y();"; - dbg() << " stream << rect.width();"; - dbg() << " stream << rect.height();"; - dbg() << " }"; + out() << " stream << (u64)m_" << parameter.name << ".size();"; + out() << " for (auto& rect : m_" << parameter.name << ") {"; + out() << " stream << rect.x();"; + out() << " stream << rect.y();"; + out() << " stream << rect.width();"; + out() << " stream << rect.height();"; + out() << " }"; } else if (parameter.type == "Gfx::ShareableBitmap") { - dbg() << " stream << m_" << parameter.name << ".shbuf_id();"; - dbg() << " stream << m_" << parameter.name << ".width();"; - dbg() << " stream << m_" << parameter.name << ".height();"; + out() << " stream << m_" << parameter.name << ".shbuf_id();"; + out() << " stream << m_" << parameter.name << ".width();"; + out() << " stream << m_" << parameter.name << ".height();"; } else { - dbg() << " stream << m_" << parameter.name << ";"; + out() << " stream << m_" << parameter.name << ";"; } } - dbg() << " return buffer;"; - dbg() << " }"; + out() << " return buffer;"; + out() << " }"; for (auto& parameter : parameters) { - dbg() << " const " << parameter.type << "& " << parameter.name << "() const { return m_" << parameter.name << "; }"; + out() << " const " << parameter.type << "& " << parameter.name << "() const { return m_" << parameter.name << "; }"; } - dbg() << "private:"; + out() << "private:"; for (auto& parameter : parameters) { - dbg() << " " << parameter.type << " m_" << parameter.name << ";"; + out() << " " << parameter.type << " m_" << parameter.name << ";"; } - dbg() << "};"; - dbg(); + out() << "};"; + out(); }; for (auto& message : endpoint.messages) { String response_name; @@ -391,72 +391,72 @@ int main(int argc, char** argv) } do_message(message.name, message.inputs, response_name); } - dbg() << "} // namespace " << endpoint.name; - dbg() << "} // namespace Messages"; - dbg(); + out() << "} // namespace " << endpoint.name; + out() << "} // namespace Messages"; + out(); - dbg() << "class " << endpoint.name << "Endpoint : public IPC::Endpoint {"; - dbg() << "public:"; - dbg() << " " << endpoint.name << "Endpoint() {}"; - dbg() << " virtual ~" << endpoint.name << "Endpoint() override {}"; - dbg() << " static int static_magic() { return " << endpoint.magic << "; }"; - dbg() << " virtual int magic() const override { return " << endpoint.magic << "; }"; - dbg() << " static String static_name() { return \"" << endpoint.name << "\"; };"; - dbg() << " virtual String name() const override { return \"" << endpoint.name << "\"; };"; - dbg() << " static OwnPtr decode_message(const ByteBuffer& buffer, size_t& size_in_bytes)"; - dbg() << " {"; - dbg() << " BufferStream stream(const_cast(buffer));"; - dbg() << " i32 message_endpoint_magic = 0;"; - dbg() << " stream >> message_endpoint_magic;"; - dbg() << " if (message_endpoint_magic != " << endpoint.magic << ") {"; + out() << "class " << endpoint.name << "Endpoint : public IPC::Endpoint {"; + out() << "public:"; + out() << " " << endpoint.name << "Endpoint() {}"; + out() << " virtual ~" << endpoint.name << "Endpoint() override {}"; + out() << " static int static_magic() { return " << endpoint.magic << "; }"; + out() << " virtual int magic() const override { return " << endpoint.magic << "; }"; + out() << " static String static_name() { return \"" << endpoint.name << "\"; };"; + out() << " virtual String name() const override { return \"" << endpoint.name << "\"; };"; + out() << " static OwnPtr decode_message(const ByteBuffer& buffer, size_t& size_in_bytes)"; + out() << " {"; + out() << " BufferStream stream(const_cast(buffer));"; + out() << " i32 message_endpoint_magic = 0;"; + out() << " stream >> message_endpoint_magic;"; + out() << " if (message_endpoint_magic != " << endpoint.magic << ") {"; #ifdef GENERATE_DEBUG_CODE - dbg() << " dbg() << \"endpoint magic \" << message_endpoint_magic << \" != " << endpoint.magic << "\";"; + sout() << " sout() << \"endpoint magic \" << message_endpoint_magic << \" != " << endpoint.magic << "\";"; #endif - dbg() << " return nullptr;"; - dbg() << " }"; - dbg() << " i32 message_id = 0;"; - dbg() << " stream >> message_id;"; - dbg() << " switch (message_id) {"; + out() << " return nullptr;"; + out() << " }"; + out() << " i32 message_id = 0;"; + out() << " stream >> message_id;"; + out() << " switch (message_id) {"; for (auto& message : endpoint.messages) { auto do_decode_message = [&](const String& name) { - dbg() << " case (int)Messages::" << endpoint.name << "::MessageID::" << name << ":"; - dbg() << " return Messages::" << endpoint.name << "::" << name << "::decode(stream, size_in_bytes);"; + out() << " case (int)Messages::" << endpoint.name << "::MessageID::" << name << ":"; + out() << " return Messages::" << endpoint.name << "::" << name << "::decode(stream, size_in_bytes);"; }; do_decode_message(message.name); if (message.is_synchronous) do_decode_message(message.response_name()); } - dbg() << " default:"; + out() << " default:"; #ifdef GENERATE_DEBUG_CODE - dbg() << " dbg() << \"Failed to decode " << endpoint.name << ".(\" << message_id << \")\";"; + sout() << " sout() << \"Failed to decode " << endpoint.name << ".(\" << message_id << \")\";"; #endif - dbg() << " return nullptr;"; + out() << " return nullptr;"; - dbg() << " }"; - dbg() << " }"; - dbg(); - dbg() << " virtual OwnPtr handle(const IPC::Message& message) override"; - dbg() << " {"; - dbg() << " switch (message.message_id()) {"; + out() << " }"; + out() << " }"; + out(); + out() << " virtual OwnPtr handle(const IPC::Message& message) override"; + out() << " {"; + out() << " switch (message.message_id()) {"; for (auto& message : endpoint.messages) { auto do_decode_message = [&](const String& name, bool returns_something) { - dbg() << " case (int)Messages::" << endpoint.name << "::MessageID::" << name << ":"; + out() << " case (int)Messages::" << endpoint.name << "::MessageID::" << name << ":"; if (returns_something) { - dbg() << " return handle(static_cast(message));"; + out() << " return handle(static_cast(message));"; } else { - dbg() << " handle(static_cast(message));"; - dbg() << " return nullptr;"; + out() << " handle(static_cast(message));"; + out() << " return nullptr;"; } }; do_decode_message(message.name, message.is_synchronous); if (message.is_synchronous) do_decode_message(message.response_name(), false); } - dbg() << " default:"; - dbg() << " return nullptr;"; + out() << " default:"; + out() << " return nullptr;"; - dbg() << " }"; - dbg() << " }"; + out() << " }"; + out() << " }"; for (auto& message : endpoint.messages) { String return_type = "void"; @@ -470,30 +470,30 @@ int main(int argc, char** argv) builder.append(">"); return_type = builder.to_string(); } - dbg() << " virtual " << return_type << " handle(const Messages::" << endpoint.name << "::" << message.name << "&) = 0;"; + out() << " virtual " << return_type << " handle(const Messages::" << endpoint.name << "::" << message.name << "&) = 0;"; } - dbg() << "private:"; - dbg() << "};"; + out() << "private:"; + out() << "};"; } #ifdef DEBUG for (auto& endpoint : endpoints) { - dbg() << "Endpoint: '" << endpoint.name << "' (magic: " << endpoint.magic << ")"; + warn() << "Endpoint: '" << endpoint.name << "' (magic: " << endpoint.magic << ")"; for (auto& message : endpoint.messages) { - dbg() << " Message: '" << message.name << "'"; - dbg() << " Sync: " << message.is_synchronous; - dbg() << " Inputs:"; + warn() << " Message: '" << message.name << "'"; + warn() << " Sync: " << message.is_synchronous; + warn() << " Inputs:"; for (auto& parameter : message.inputs) - dbg() << " Parameter: " << parameter.name << " (" << parameter.type << ")"; + warn() << " Parameter: " << parameter.name << " (" << parameter.type << ")"; if (message.inputs.is_empty()) - dbg() << " (none)"; + warn() << " (none)"; if (message.is_synchronous) { - dbg() << " Outputs:"; + warn() << " Outputs:"; for (auto& parameter : message.outputs) - dbg() << " Parameter: " << parameter.name << " (" << parameter.type << ")"; + warn() << " Parameter: " << parameter.name << " (" << parameter.type << ")"; if (message.outputs.is_empty()) - dbg() << " (none)"; + warn() << " (none)"; } } } diff --git a/Libraries/LibWeb/CodeGenerators/Generate_CSS_PropertyID_cpp/Generate_CSS_PropertyID_cpp.cpp b/Libraries/LibWeb/CodeGenerators/Generate_CSS_PropertyID_cpp/Generate_CSS_PropertyID_cpp.cpp index f31fe62310..2b34a62cd8 100644 --- a/Libraries/LibWeb/CodeGenerators/Generate_CSS_PropertyID_cpp/Generate_CSS_PropertyID_cpp.cpp +++ b/Libraries/LibWeb/CodeGenerators/Generate_CSS_PropertyID_cpp/Generate_CSS_PropertyID_cpp.cpp @@ -58,36 +58,36 @@ int main(int argc, char** argv) auto json = JsonValue::from_string(file->read_all()); ASSERT(json.is_object()); - dbg() << "#include "; - dbg() << "#include "; - dbg() << "namespace Web {"; - dbg() << "namespace CSS {"; + out() << "#include "; + out() << "#include "; + out() << "namespace Web {"; + out() << "namespace CSS {"; - dbg() << "PropertyID property_id_from_string(const StringView& string) {"; + out() << "PropertyID property_id_from_string(const StringView& string) {"; json.as_object().for_each_member([&](auto& name, auto& value) { ASSERT(value.is_object()); - dbg() << " if (string == \"" << name << "\")"; - dbg() << " return PropertyID::" << title_casify(name) << ";"; + out() << " if (string == \"" << name << "\")"; + out() << " return PropertyID::" << title_casify(name) << ";"; }); - dbg() << " return PropertyID::Invalid;"; + out() << " return PropertyID::Invalid;"; - dbg() << "}"; + out() << "}"; - dbg() << "const char* string_from_property_id(PropertyID property_id) {"; - dbg() << " switch (property_id) {"; + out() << "const char* string_from_property_id(PropertyID property_id) {"; + out() << " switch (property_id) {"; json.as_object().for_each_member([&](auto& name, auto& value) { ASSERT(value.is_object()); - dbg() << " case PropertyID::" << title_casify(name) << ":"; - dbg() << " return \"" << name << "\";"; + out() << " case PropertyID::" << title_casify(name) << ":"; + out() << " return \"" << name << "\";"; }); - dbg() << " default:"; - dbg() << " return \"(invalid CSS::PropertyID)\";"; - dbg() << " }"; - dbg() << "}"; - dbg() << "}"; - dbg() << "}"; + out() << " default:"; + out() << " return \"(invalid CSS::PropertyID)\";"; + out() << " }"; + out() << "}"; + out() << "}"; + out() << "}"; return 0; } diff --git a/Libraries/LibWeb/CodeGenerators/Generate_CSS_PropertyID_h/Generate_CSS_PropertyID_h.cpp b/Libraries/LibWeb/CodeGenerators/Generate_CSS_PropertyID_h/Generate_CSS_PropertyID_h.cpp index 8ebe39deee..04cd3d9278 100644 --- a/Libraries/LibWeb/CodeGenerators/Generate_CSS_PropertyID_h/Generate_CSS_PropertyID_h.cpp +++ b/Libraries/LibWeb/CodeGenerators/Generate_CSS_PropertyID_h/Generate_CSS_PropertyID_h.cpp @@ -58,21 +58,21 @@ int main(int argc, char** argv) auto json = JsonValue::from_string(file->read_all()); ASSERT(json.is_object()); - dbg() << "#pragma once"; - dbg() << "#include "; - dbg() << "#include "; + out() << "#pragma once"; + out() << "#include "; + out() << "#include "; - dbg() << "namespace Web {"; - dbg() << "namespace CSS {"; - dbg() << "enum class PropertyID {"; - dbg() << " Invalid,"; + out() << "namespace Web {"; + out() << "namespace CSS {"; + out() << "enum class PropertyID {"; + out() << " Invalid,"; json.as_object().for_each_member([&](auto& name, auto& value) { ASSERT(value.is_object()); - dbg() << " " << title_casify(name) << ","; + out() << " " << title_casify(name) << ","; }); - dbg() << "};\n\ + out() << "};\n\ PropertyID property_id_from_string(const StringView&);\n\ const char* string_from_property_id(PropertyID);\n\ }\n\