зеркало из https://github.com/microsoft/xlang.git
Fix indentation for idl output (Take 2) (#260)
* Fix indentation for idl output Do not use hardcoded indentation for specific output types, since some of them are used in different contexts. For example custom attributes may be used for both classes and their methods. To use proper indentation use same approach as python tool that uses indent_guard class to automatically increase indentation in scope and specialize writer::write_impl() methods to automatically indent output for each line that starts on new line. * Move src/tool/idl to samples/meta_reader * Address review notes * Make meta_reader cmake file self-contained * add cmake policy statement for CMP0076 * added winml tutorial reference to samples/readme.md * modified CODEOWNERS to address moving IDL -> samples
This commit is contained in:
Родитель
16bc9886fa
Коммит
c1c1fd9f99
|
@ -21,12 +21,12 @@
|
|||
/src/test/cpp/ @kennykerr
|
||||
/src/tool/cpp/ @kennykerr
|
||||
|
||||
/src/tool/idl/ @kennykerr
|
||||
|
||||
/src/tool/natvis/ @Scottj1s
|
||||
|
||||
/src/test/python/ @devhawk
|
||||
/src/tool/python/ @devhawk
|
||||
|
||||
/samples @devhawk
|
||||
/samples/python/ @devhawk
|
||||
|
||||
|
||||
|
|
|
@ -0,0 +1,60 @@
|
|||
cmake_minimum_required(VERSION 3.9)
|
||||
|
||||
if (${CMAKE_VERSION} VERSION_GREATER_EQUAL "3.13")
|
||||
cmake_policy(SET CMP0076 NEW)
|
||||
endif()
|
||||
|
||||
project(meta_reader)
|
||||
|
||||
set(XLANG_LIBRARY_PATH "${CMAKE_CURRENT_SOURCE_DIR}/../../src/library")
|
||||
|
||||
set(CMAKE_CXX_STANDARD 17)
|
||||
set(CMAKE_CXX_STANDARD_REQUIRED ON)
|
||||
|
||||
add_executable(meta_reader "")
|
||||
target_sources(meta_reader PUBLIC main.cpp pch.cpp)
|
||||
target_include_directories(meta_reader PUBLIC ${XLANG_LIBRARY_PATH})
|
||||
|
||||
function(ADD_OBJECT_DEPENDS file dependency)
|
||||
get_source_file_property(cur_obj_depends ${file} OBJECT_DEPENDS)
|
||||
if (${cur_obj_depends} STREQUAL "NOTFOUND")
|
||||
set(new_obj_depends "${pch_output_file_name}")
|
||||
else()
|
||||
set(new_obj_depends "${cur_obj_depends};${dependency}")
|
||||
endif()
|
||||
set_source_files_properties(${file} PROPERTIES OBJECT_DEPENDS ${new_obj_depends})
|
||||
endfunction(ADD_OBJECT_DEPENDS)
|
||||
|
||||
function(TARGET_CONFIG_MSVC_PCH target pch_cpp pch_header)
|
||||
get_target_property(target_name ${target} NAME)
|
||||
set(pch_output_file_name "${target_name}.pch")
|
||||
set(pch_output_file "\"${CMAKE_CURRENT_BINARY_DIR}/${pch_output_file_name}\"")
|
||||
|
||||
get_target_property(sources ${target} SOURCES)
|
||||
foreach(file ${sources})
|
||||
if (${file} STREQUAL ${pch_cpp})
|
||||
set_source_files_properties(${file}
|
||||
PROPERTIES
|
||||
COMPILE_FLAGS " /Yc${pch_header} /Fp${pch_output_file}"
|
||||
OBJECT_OUTPUTS ${pch_output_file_name})
|
||||
else()
|
||||
set_source_files_properties(${file} PROPERTIES COMPILE_FLAGS " /Yu${pch_header} /Fp${pch_output_file}")
|
||||
ADD_OBJECT_DEPENDS(${file} ${pch_output_file_name})
|
||||
endif()
|
||||
endforeach()
|
||||
|
||||
set_target_properties(${target} PROPERTIES PCH_OUTPUT_FILE ${pch_output_file})
|
||||
set_property(GLOBAL APPEND PROPERTY PCH_OUTPUT_FILES ${pch_output_file})
|
||||
endfunction(TARGET_CONFIG_MSVC_PCH)
|
||||
|
||||
if (WIN32)
|
||||
add_definitions(-DNOMINMAX)
|
||||
endif()
|
||||
|
||||
if (MSVC)
|
||||
TARGET_CONFIG_MSVC_PCH(meta_reader pch.cpp pch.h)
|
||||
target_link_libraries(meta_reader)
|
||||
else()
|
||||
target_link_libraries(meta_reader c++ c++abi c++experimental)
|
||||
target_link_libraries(meta_reader -lpthread)
|
||||
endif()
|
|
@ -14,7 +14,26 @@ template <typename...T> overloaded(T...)->overloaded<T...>;
|
|||
struct writer : writer_base<writer>
|
||||
{
|
||||
using writer_base<writer>::write;
|
||||
|
||||
struct indent_guard
|
||||
{
|
||||
explicit indent_guard(writer& w, int32_t offset = 1) noexcept : _writer(w), _offset(offset)
|
||||
{
|
||||
_writer.indent += _offset;
|
||||
}
|
||||
|
||||
~indent_guard()
|
||||
{
|
||||
_writer.indent -= _offset;
|
||||
}
|
||||
|
||||
private:
|
||||
writer& _writer;
|
||||
int32_t _offset;
|
||||
};
|
||||
|
||||
std::string_view current;
|
||||
int32_t indent{};
|
||||
|
||||
std::vector<std::pair<GenericParam, GenericParam>> generic_param_stack;
|
||||
|
||||
|
@ -47,6 +66,76 @@ struct writer : writer_base<writer>
|
|||
return generic_param_guard{ this };
|
||||
}
|
||||
|
||||
void write_indent()
|
||||
{
|
||||
for (int32_t i = 0; i < indent; i++)
|
||||
{
|
||||
writer_base::write_impl(" ");
|
||||
}
|
||||
}
|
||||
|
||||
void write_impl(std::string_view const& value)
|
||||
{
|
||||
std::string_view::size_type current_pos{ 0 };
|
||||
auto on_new_line = back() == '\n';
|
||||
|
||||
while (true)
|
||||
{
|
||||
const auto pos = value.find('\n', current_pos);
|
||||
|
||||
if (pos == std::string_view::npos)
|
||||
{
|
||||
if (current_pos < value.size())
|
||||
{
|
||||
if (on_new_line)
|
||||
{
|
||||
write_indent();
|
||||
}
|
||||
|
||||
writer_base::write_impl(value.substr(current_pos));
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
auto current_line = value.substr(current_pos, pos - current_pos + 1);
|
||||
auto empty_line = current_line[0] == '\n';
|
||||
|
||||
if (on_new_line && !empty_line)
|
||||
{
|
||||
write_indent();
|
||||
}
|
||||
|
||||
writer_base::write_impl(current_line);
|
||||
|
||||
on_new_line = true;
|
||||
current_pos = pos + 1;
|
||||
}
|
||||
}
|
||||
|
||||
void write_impl(char const value)
|
||||
{
|
||||
if (back() == '\n' && value != '\n')
|
||||
{
|
||||
write_indent();
|
||||
}
|
||||
|
||||
writer_base::write_impl(value);
|
||||
}
|
||||
|
||||
template <typename... Args>
|
||||
std::string write_temp(std::string_view const& value, Args const& ... args)
|
||||
{
|
||||
auto restore_indent = indent;
|
||||
indent = 0;
|
||||
|
||||
auto result = writer_base::write_temp(value, args...);
|
||||
|
||||
indent = restore_indent;
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
void write_value(bool value)
|
||||
{
|
||||
write(value ? "TRUE"sv : "FALSE"sv);
|
||||
|
@ -365,35 +454,35 @@ struct writer : writer_base<writer>
|
|||
{
|
||||
std::visit(overloaded{
|
||||
[this](ElemSig::SystemType arg)
|
||||
{
|
||||
write(arg.name);
|
||||
},
|
||||
{
|
||||
write(arg.name);
|
||||
},
|
||||
[this](ElemSig::EnumValue arg)
|
||||
{
|
||||
auto const enumerators = find_enumerators(arg);
|
||||
if (enumerators.empty())
|
||||
{
|
||||
std::visit([this](auto&& value) { write_value(value); }, arg.value);
|
||||
}
|
||||
else
|
||||
{
|
||||
bool first = true;
|
||||
for (auto const& enumerator : enumerators)
|
||||
auto const enumerators = find_enumerators(arg);
|
||||
if (enumerators.empty())
|
||||
{
|
||||
if (!first)
|
||||
{
|
||||
write(" | ");
|
||||
}
|
||||
write("%.%.%", arg.type.m_typedef.TypeNamespace(), arg.type.m_typedef.TypeName(), enumerator.Name());
|
||||
first = false;
|
||||
std::visit([this](auto&& value) { write_value(value); }, arg.value);
|
||||
}
|
||||
}
|
||||
},
|
||||
else
|
||||
{
|
||||
bool first = true;
|
||||
for (auto const& enumerator : enumerators)
|
||||
{
|
||||
if (!first)
|
||||
{
|
||||
write(" | ");
|
||||
}
|
||||
write("%.%.%", arg.type.m_typedef.TypeNamespace(), arg.type.m_typedef.TypeName(), enumerator.Name());
|
||||
first = false;
|
||||
}
|
||||
}
|
||||
},
|
||||
[this](auto&& arg)
|
||||
{
|
||||
write_value(arg);
|
||||
}
|
||||
}, std::get<ElemSig>(arg.value).value);
|
||||
{
|
||||
write_value(arg);
|
||||
}
|
||||
}, std::get<ElemSig>(arg.value).value);
|
||||
}
|
||||
|
||||
void write(NamedArgSig const& arg)
|
||||
|
@ -405,19 +494,18 @@ struct writer : writer_base<writer>
|
|||
{
|
||||
auto const& args = arg.FixedArgs();
|
||||
|
||||
write_printf("\n [Windows.Foundation.Metadata.GuidAttribute(%08X-%04X-%04X-%02X%02X-%02X%02X%02X%02X%02X%02X)]"
|
||||
, std::get<uint32_t>(std::get<ElemSig>(args[0].value).value)
|
||||
, std::get<uint16_t>(std::get<ElemSig>(args[1].value).value)
|
||||
, std::get<uint16_t>(std::get<ElemSig>(args[2].value).value)
|
||||
, std::get<uint8_t>(std::get<ElemSig>(args[3].value).value)
|
||||
, std::get<uint8_t>(std::get<ElemSig>(args[4].value).value)
|
||||
, std::get<uint8_t>(std::get<ElemSig>(args[5].value).value)
|
||||
, std::get<uint8_t>(std::get<ElemSig>(args[6].value).value)
|
||||
, std::get<uint8_t>(std::get<ElemSig>(args[7].value).value)
|
||||
, std::get<uint8_t>(std::get<ElemSig>(args[8].value).value)
|
||||
, std::get<uint8_t>(std::get<ElemSig>(args[9].value).value)
|
||||
, std::get<uint8_t>(std::get<ElemSig>(args[10].value).value)
|
||||
);
|
||||
write_printf("[Windows.Foundation.Metadata.GuidAttribute(%08X-%04X-%04X-%02X%02X-%02X%02X%02X%02X%02X%02X)]",
|
||||
std::get<uint32_t>(std::get<ElemSig>(args[0].value).value),
|
||||
std::get<uint16_t>(std::get<ElemSig>(args[1].value).value),
|
||||
std::get<uint16_t>(std::get<ElemSig>(args[2].value).value),
|
||||
std::get<uint8_t>(std::get<ElemSig>(args[3].value).value),
|
||||
std::get<uint8_t>(std::get<ElemSig>(args[4].value).value),
|
||||
std::get<uint8_t>(std::get<ElemSig>(args[5].value).value),
|
||||
std::get<uint8_t>(std::get<ElemSig>(args[6].value).value),
|
||||
std::get<uint8_t>(std::get<ElemSig>(args[7].value).value),
|
||||
std::get<uint8_t>(std::get<ElemSig>(args[8].value).value),
|
||||
std::get<uint8_t>(std::get<ElemSig>(args[9].value).value),
|
||||
std::get<uint8_t>(std::get<ElemSig>(args[10].value).value));
|
||||
}
|
||||
|
||||
void write(CustomAttribute const& attr)
|
||||
|
@ -431,7 +519,7 @@ struct writer : writer_base<writer>
|
|||
return;
|
||||
}
|
||||
|
||||
write("\n [%.%", name.first, name.second);
|
||||
write("[%.%", name.first, name.second);
|
||||
|
||||
bool first = true;
|
||||
for (auto const& fixed_arg : sig.FixedArgs())
|
||||
|
@ -469,6 +557,11 @@ struct writer : writer_base<writer>
|
|||
}
|
||||
};
|
||||
|
||||
void write_custom_attribute(writer& w, CustomAttribute const& attr)
|
||||
{
|
||||
w.write("\n%", attr);
|
||||
}
|
||||
|
||||
void write_type_name(writer& w, std::string_view name)
|
||||
{
|
||||
w.write(name);
|
||||
|
@ -493,41 +586,37 @@ void write_type_name(writer& w, std::string_view name)
|
|||
|
||||
void write_enum_field(writer& w, Field const& field)
|
||||
{
|
||||
writer::indent_guard _{ w };
|
||||
|
||||
if (auto const& constant = field.Constant())
|
||||
{
|
||||
w.write("\n % = %,",
|
||||
field.Name(),
|
||||
constant);
|
||||
w.write("\n% = %,", field.Name(), constant);
|
||||
}
|
||||
}
|
||||
|
||||
void write_enum(writer& w, TypeDef const& type)
|
||||
{
|
||||
for (auto const& attr : type.CustomAttribute())
|
||||
{
|
||||
w.write(attr);
|
||||
}
|
||||
writer::indent_guard _{ w };
|
||||
|
||||
w.write("\n enum %\n {%\n };\n",
|
||||
w.write("%\nenum %\n{%\n};\n",
|
||||
bind_each<write_custom_attribute>(type.CustomAttribute()),
|
||||
type.TypeName(),
|
||||
bind_each<write_enum_field>(type.FieldList()));
|
||||
}
|
||||
|
||||
void write_struct_field(writer& w, Field const& field)
|
||||
{
|
||||
w.write("\n % %;",
|
||||
field.Signature().Type(),
|
||||
field.Name());
|
||||
writer::indent_guard _{ w };
|
||||
|
||||
w.write("\n% %;", field.Signature().Type(), field.Name());
|
||||
}
|
||||
|
||||
void write_struct(writer& w, TypeDef const& type)
|
||||
{
|
||||
for (auto const& attr : type.CustomAttribute())
|
||||
{
|
||||
w.write(attr);
|
||||
}
|
||||
writer::indent_guard _{ w };
|
||||
|
||||
w.write("\n struct %\n {%\n };\n",
|
||||
w.write("%\nstruct %\n{%\n};\n",
|
||||
bind_each<write_custom_attribute>(type.CustomAttribute()),
|
||||
type.TypeName(),
|
||||
bind_each<write_struct_field>(type.FieldList()));
|
||||
}
|
||||
|
@ -536,6 +625,7 @@ void write_delegate(writer& w, TypeDef const& type)
|
|||
{
|
||||
auto guard{ w.push_generic_params(type.GenericParam()) };
|
||||
auto methods = type.MethodList();
|
||||
writer::indent_guard _{ w };
|
||||
|
||||
auto method = std::find_if(begin(methods), end(methods), [](auto&& method)
|
||||
{
|
||||
|
@ -547,22 +637,20 @@ void write_delegate(writer& w, TypeDef const& type)
|
|||
throw_invalid("Delegate's Invoke method not found");
|
||||
}
|
||||
|
||||
for (auto const& attr : type.CustomAttribute())
|
||||
{
|
||||
w.write(attr);
|
||||
}
|
||||
|
||||
w.write("\n delegate % %(%);\n", method.Signature().ReturnType(), bind<write_type_name>(type.TypeName()), method);
|
||||
w.write("%\ndelegate % %(%);\n",
|
||||
bind_each<write_custom_attribute>(type.CustomAttribute()),
|
||||
method.Signature().ReturnType(),
|
||||
bind<write_type_name>(type.TypeName()),
|
||||
method);
|
||||
}
|
||||
|
||||
void write_method(writer& w, MethodDef const& method)
|
||||
{
|
||||
for (auto const& attr : method.CustomAttribute())
|
||||
{
|
||||
w.write(attr);
|
||||
}
|
||||
|
||||
w.write("\n % %(%);", method.Signature().ReturnType(), method.Name(), method);
|
||||
w.write("%\n% %(%);",
|
||||
bind_each<write_custom_attribute>(method.CustomAttribute()),
|
||||
method.Signature().ReturnType(),
|
||||
method.Name(),
|
||||
method);
|
||||
}
|
||||
|
||||
void write_method_semantic(writer& w, MethodSemantics const& method_semantic, MethodDef& method)
|
||||
|
@ -591,10 +679,7 @@ void write_method_semantic(writer& w, MethodSemantics const& method_semantic, Me
|
|||
if (method < other_method)
|
||||
{
|
||||
// First accessor seen for this property
|
||||
for (auto const& attr : property.CustomAttribute())
|
||||
{
|
||||
w.write(attr);
|
||||
}
|
||||
w.write(bind_each<write_custom_attribute>(property.CustomAttribute()));
|
||||
}
|
||||
|
||||
if (semantic.Getter())
|
||||
|
@ -605,36 +690,34 @@ void write_method_semantic(writer& w, MethodSemantics const& method_semantic, Me
|
|||
{
|
||||
xlang::throw_invalid("Invalid semantic: properties can only have a setter and/or getter");
|
||||
}
|
||||
w.write("\n % %;", property.Type().Type(), property.Name());
|
||||
w.write("\n% %;", property.Type().Type(), property.Name());
|
||||
++method;
|
||||
}
|
||||
else
|
||||
{
|
||||
XLANG_ASSERT(semantic.Getter());
|
||||
w.write("\n % % { get; };", property.Type().Type(), property.Name());
|
||||
w.write("\n% % { get; };", property.Type().Type(), property.Name());
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
XLANG_ASSERT(semantic.Setter());
|
||||
w.write("\n % % { set; };", property.Type().Type(), property.Name());
|
||||
w.write("\n% % { set; };", property.Type().Type(), property.Name());
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
XLANG_ASSERT(distance(accessors) == 1);
|
||||
for (auto const& attr : property.CustomAttribute())
|
||||
{
|
||||
w.write(attr);
|
||||
}
|
||||
w.write(bind_each<write_custom_attribute>(property.CustomAttribute()));
|
||||
|
||||
if (semantic.Getter())
|
||||
{
|
||||
w.write("\n % % { get; };", property.Type().Type(), property.Name());
|
||||
w.write("\n% % { get; };", property.Type().Type(), property.Name());
|
||||
}
|
||||
else
|
||||
{
|
||||
XLANG_ASSERT(semantic.Setter());
|
||||
w.write("\n % % { set; };", property.Type().Type(), property.Name());
|
||||
w.write("\n% % { set; };", property.Type().Type(), property.Name());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -659,10 +742,7 @@ void write_method_semantic(writer& w, MethodSemantics const& method_semantic, Me
|
|||
if (method < other_method)
|
||||
{
|
||||
// First accessor seen for this event
|
||||
for (auto const& attr : event.CustomAttribute())
|
||||
{
|
||||
w.write(attr);
|
||||
}
|
||||
w.write(bind_each<write_custom_attribute>(event.CustomAttribute()));
|
||||
}
|
||||
|
||||
if (semantic.AddOn())
|
||||
|
@ -673,42 +753,47 @@ void write_method_semantic(writer& w, MethodSemantics const& method_semantic, Me
|
|||
{
|
||||
xlang::throw_invalid("Invalid semantic: events can only have a add and/or remove");
|
||||
}
|
||||
w.write("\n % %;", event.EventType(), event.Name());
|
||||
w.write("\n% %;", event.EventType(), event.Name());
|
||||
++method;
|
||||
}
|
||||
else
|
||||
{
|
||||
XLANG_ASSERT(semantic.AddOn());
|
||||
w.write("\n % % { add; };", event.EventType(), event.Name());
|
||||
w.write("\n% % { add; };", event.EventType(), event.Name());
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
XLANG_ASSERT(semantic.RemoveOn());
|
||||
w.write("\n % % { remove; };", event.EventType(), event.Name());
|
||||
w.write("\n% % { remove; };", event.EventType(), event.Name());
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
XLANG_ASSERT(distance(accessors) == 1);
|
||||
for (auto const& attr : event.CustomAttribute())
|
||||
{
|
||||
w.write(attr);
|
||||
}
|
||||
w.write(bind_each<write_custom_attribute>(event.CustomAttribute()));
|
||||
|
||||
if (semantic.AddOn())
|
||||
{
|
||||
w.write("\n % % { add; };", event.EventType(), event.Name());
|
||||
w.write("\n% % { add; };", event.EventType(), event.Name());
|
||||
}
|
||||
else
|
||||
{
|
||||
XLANG_ASSERT(semantic.RemoveOn());
|
||||
w.write("\n % % { remove; };", event.EventType(), event.Name());
|
||||
w.write("\n% % { remove; };", event.EventType(), event.Name());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void write_required_interface(writer& w, InterfaceImpl const& interface_impl)
|
||||
{
|
||||
writer::indent_guard _{ w };
|
||||
|
||||
w.write("\n%", interface_impl.Interface());
|
||||
}
|
||||
|
||||
void write_required(writer& w, std::string_view const& requires, TypeDef const& type)
|
||||
{
|
||||
auto interfaces{ type.InterfaceImpl() };
|
||||
|
@ -718,7 +803,9 @@ void write_required(writer& w, std::string_view const& requires, TypeDef const&
|
|||
return;
|
||||
}
|
||||
|
||||
w.write(" %\n %", requires, bind_list(",\n ", interfaces));
|
||||
w.write(" %%",
|
||||
requires,
|
||||
bind_list<write_required_interface>(",", interfaces));
|
||||
}
|
||||
|
||||
void write_interface_methods(writer& w, TypeDef const& type)
|
||||
|
@ -726,6 +813,7 @@ void write_interface_methods(writer& w, TypeDef const& type)
|
|||
auto const& methods = type.MethodList();
|
||||
auto const& properties = type.PropertyList();
|
||||
auto const& events = type.EventList();
|
||||
writer::indent_guard _{ w };
|
||||
|
||||
auto method_semantic = [&properties, &events](MethodDef const& method) -> MethodSemantics
|
||||
{
|
||||
|
@ -769,13 +857,10 @@ void write_interface_methods(writer& w, TypeDef const& type)
|
|||
void write_interface(writer& w, TypeDef const& type)
|
||||
{
|
||||
auto guard = w.push_generic_params(type.GenericParam());
|
||||
writer::indent_guard _{ w };
|
||||
|
||||
for (auto const& attr : type.CustomAttribute())
|
||||
{
|
||||
w.write(attr);
|
||||
}
|
||||
|
||||
w.write("\n interface %%\n {%\n };\n",
|
||||
w.write("%\ninterface %%\n{%\n};\n",
|
||||
bind_each<write_custom_attribute>(type.CustomAttribute()),
|
||||
bind<write_type_name>(type.TypeName()),
|
||||
bind<write_required>("requires", type),
|
||||
bind<write_interface_methods>(type));
|
||||
|
@ -784,13 +869,10 @@ void write_interface(writer& w, TypeDef const& type)
|
|||
void write_class(writer& w, TypeDef const& type)
|
||||
{
|
||||
auto guard = w.push_generic_params(type.GenericParam());
|
||||
writer::indent_guard _{ w };
|
||||
|
||||
for (auto const& attr : type.CustomAttribute())
|
||||
{
|
||||
w.write(attr);
|
||||
}
|
||||
|
||||
w.write("\n runtimeclass %%\n {\n };\n",
|
||||
w.write("%\nruntimeclass %%\n{\n};\n",
|
||||
bind_each<write_custom_attribute>(type.CustomAttribute()),
|
||||
bind<write_type_name>(type.TypeName()),
|
||||
bind<write_required>(":", type));
|
||||
}
|
||||
|
@ -853,28 +935,28 @@ int main(int const argc, char** argv)
|
|||
w.flush_to_console();
|
||||
task_group group;
|
||||
|
||||
for (auto&& ns : c.namespaces())
|
||||
for (auto const& [ns, members] : c.namespaces())
|
||||
{
|
||||
group.add([&]
|
||||
group.add([&, &ns = ns, &members = members]
|
||||
{
|
||||
if (!f.includes(ns.second))
|
||||
if (!f.includes(members))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
writer w;
|
||||
w.current = ns.first;
|
||||
w.current = ns;
|
||||
|
||||
w.write("\nnamespace %\n{%%%%%}\n",
|
||||
w.current,
|
||||
f.bind_each<write_enum>(ns.second.enums),
|
||||
f.bind_each<write_struct>(ns.second.structs),
|
||||
f.bind_each<write_delegate>(ns.second.delegates),
|
||||
f.bind_each<write_interface>(ns.second.interfaces),
|
||||
f.bind_each<write_class>(ns.second.classes));
|
||||
ns,
|
||||
f.bind_each<write_enum>(members.enums),
|
||||
f.bind_each<write_struct>(members.structs),
|
||||
f.bind_each<write_delegate>(members.delegates),
|
||||
f.bind_each<write_interface>(members.interfaces),
|
||||
f.bind_each<write_class>(members.classes));
|
||||
|
||||
auto filename{ out };
|
||||
filename += w.current;
|
||||
filename += ns;
|
||||
filename += ".idl";
|
||||
w.flush_to_file(filename);
|
||||
});
|
|
@ -0,0 +1,7 @@
|
|||
# Samples
|
||||
|
||||
## Folder Structure
|
||||
|
||||
* **/meta_reader** sample metadata reader that generates [MIDL 3](http://docs.microsoft.com/en-us/uwp/midl-3/) files from ECMA-335 metadata.
|
||||
* **/python/winml_tutorial** a port of the [WinML C++/WinRT tutorial](https://docs.microsoft.com/en-us/windows/ai/get-started-desktop)
|
||||
to Python
|
|
@ -114,9 +114,7 @@ Eventually, source in the PAL will be split into separate folders based on under
|
|||
|
||||
The **/tool** folder contains the tools provided in support of xlang development. This includes tools for working with idl and winmd files as well as for generating language projections.
|
||||
|
||||
* **/tool/cpp** implements the tool that generates the C++ 17 language projection. Currently, the generated projection is Windows only, but the tool will be updated to generate cross-platform compatible code.
|
||||
|
||||
* **/tool/idl** implements a tool that generates [MIDL 3](http://docs.microsoft.com/en-us/uwp/midl-3/) files from ECMA-335 metadata.
|
||||
* **/tool/cppwinrt** implements the tool that generates the C++ 17 language projection. Currently, the generated projection is Windows only, but the tool will be updated to generate cross-platform compatible code.
|
||||
|
||||
* **/tool/natviz** implements a [Natvis visualization](http://docs.microsoft.com/en-us/visualstudio/debugger/create-custom-views-of-native-objects) of C++/WinRT components for the Visual Studio debugger 2017. Over time, this tool will be updated to support visualization of xlang components.
|
||||
|
||||
|
|
|
@ -1,7 +1,6 @@
|
|||
cmake_minimum_required(VERSION 3.9)
|
||||
|
||||
add_subdirectory(abi)
|
||||
add_subdirectory(idl)
|
||||
add_subdirectory(python)
|
||||
add_subdirectory(cppxlang)
|
||||
|
||||
|
|
|
@ -1,15 +0,0 @@
|
|||
cmake_minimum_required(VERSION 3.9)
|
||||
|
||||
project(idl)
|
||||
|
||||
add_executable(idl "")
|
||||
target_sources(idl PUBLIC main.cpp pch.cpp)
|
||||
target_include_directories(idl PUBLIC ${XLANG_LIBRARY_PATH})
|
||||
|
||||
if (WIN32)
|
||||
TARGET_CONFIG_MSVC_PCH(idl pch.cpp pch.h)
|
||||
target_link_libraries(idl windowsapp ole32 shlwapi)
|
||||
else()
|
||||
target_link_libraries(idl c++ c++abi c++experimental)
|
||||
target_link_libraries(idl -lpthread)
|
||||
endif()
|
Загрузка…
Ссылка в новой задаче