"${CMAKE_CURRENT_SOURCE_DIR}/css_selector.cxx"
"${CMAKE_CURRENT_SOURCE_DIR}/css_tokeniser.cxx"
"${CMAKE_CURRENT_SOURCE_DIR}/css_util.cxx"
+ "${CMAKE_CURRENT_SOURCE_DIR}/css_rule.cxx"
"${CMAKE_CURRENT_SOURCE_DIR}/css_parser.cxx"
"${RAGEL_ragel_css_selector_parser_OUTPUTS}"
"${RAGEL_ragel_css_rule_parser_OUTPUTS}"
#include "css_parser.hxx"
#include "css_tokeniser.hxx"
+#include "css_selector.hxx"
+#include "css_rule.hxx"
#include <vector>
#include <unicode/utf8.h>
return empty_block_vec;
}
+ auto get_token_or_empty() const -> const css_parser_token& {
+ if (content.index() == 2) {
+ return std::get<css_parser_token>(content);
+ }
+
+ return css_parser_eof_token();
+ }
+
auto token_type_str(void) const -> const char *
{
const auto *ret = "";
if (simple_block != children.end()) {
/*
* We have a component and a simple block,
- * so we can parse a declaration
+ * so we can parse a selector and then extract
+ * declarations from a simple block
*/
/* First, tag all components as preamble */
- for (auto it = children.begin(); it != simple_block; ++it) {
- (*it)->tag = css_consumed_block::parser_tag_type::css_selector;
- }
+ auto selector_it = children.cbegin();
+
+ auto selector_token_functor = [&selector_it,&simple_block](void)
+ -> const css_parser_token & {
+ for (;;) {
+ if (selector_it == simple_block) {
+ return css_parser_eof_token();
+ }
+
+ const auto &ret = (*selector_it)->get_token_or_empty();
+
+ ++selector_it;
+
+ if (ret.type != css_parser_token::token_type::eof_token) {
+ return ret;
+ }
+ }
+ };
+
+ auto selectors_vec = process_selector_tokens(pool, selector_token_functor);
+
+ auto decls_it = (*simple_block)->get_blocks_or_empty().cbegin();
+ auto decls_end = (*simple_block)->get_blocks_or_empty().cend();
+ auto declaration_token_functor = [&decls_it,&decls_end](void)
+ -> const css_parser_token & {
+ for (;;) {
+ if (decls_it == decls_end) {
+ return css_parser_eof_token();
+ }
+
+ const auto &ret = (*decls_it)->get_token_or_empty();
+
+ ++decls_it;
+
+ if (ret.type != css_parser_token::token_type::eof_token) {
+ return ret;
+ }
+ }
+ };
+
+ auto declarations_vec = process_declaration_tokens(pool,
+ declaration_token_functor);
}
}
}
namespace rspamd::css {
-INIT_LOG_MODULE(chartable)
-
auto parse_css (rspamd_mempool_t *pool, const std::string_view &st) ->
tl::expected<std::unique_ptr<css_style_sheet>,css_parse_error>;
--- /dev/null
+/*-
+ * Copyright 2021 Vsevolod Stakhov
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "css_rule.hxx"
+
+namespace rspamd::css {
+
+auto process_declaration_tokens(rspamd_mempool_t *pool,
+ const tokeniser_gen_functor &next_token_functor)
+ -> declarations_vec
+{
+ declarations_vec ret;
+
+ return ret; /* copy elision */
+}
+}
\ No newline at end of file
#include "css_value.hxx"
#include "css_property.hxx"
+#include "css_tokeniser.hxx"
#include <vector>
#include <memory>
constexpr const css_property& get_prop(void) const { return prop; }
};
+using declarations_vec = std::vector<std::unique_ptr<css_rule>>;
+
+auto process_declaration_tokens(rspamd_mempool_t *pool,
+ const tokeniser_gen_functor &next_token_functor)
+ -> declarations_vec;
+
}
/* Make rules hashable by property */
namespace rspamd::css {
-tl::expected<css_selector,css_parse_error> css_selector::from_bytes (const char *input,
- size_t inlen)
+auto process_selector_tokens(rspamd_mempool_t *pool,
+ const tokeniser_gen_functor &next_token_functor)
+ -> selectors_vec
{
- return tl::unexpected{css_parse_error(css_parse_error_type::PARSE_ERROR_NYI)};
+ selectors_vec ret;
+
+ return ret; /* copy elision */
}
}
#include <variant>
#include <string>
#include <optional>
-#include "contrib/expected/expected.hpp"
+#include <vector>
+#include <functional>
#include "parse_error.hxx"
#include "css_tokeniser.hxx"
#include "html_tags.h"
return std::string_view(std::get<std::string>(value));
}
return std::nullopt;
- }
-
- static tl::expected<css_selector,css_parse_error> from_bytes (const char *input,
- size_t inlen);
+ };
};
+using selectors_vec = std::vector<std::unique_ptr<css_selector>>;
+/*
+ * Consume selectors token and split them to the list of selectors
+ */
+auto process_selector_tokens(rspamd_mempool_t *pool,
+ const tokeniser_gen_functor &next_token_functor)
+ -> selectors_vec;
}
#include <utility>
#include <variant>
#include <list>
+#include <functional>
#include "mem_pool.h"
namespace rspamd::css {
auto debug_token_str() -> std::string;
};
+static auto css_parser_eof_token(void) -> const css_parser_token & {
+ static css_parser_token eof_tok {
+ css_parser_token::token_type::eof_token,
+ css_parser_token_placeholder()
+ };
+
+ return eof_tok;
+}
+
/* Ensure that parser tokens are simple enough */
/*
* compiler must implement P0602 "variant and optional should propagate copy/move triviality"
auto consume_ident() -> struct css_parser_token;
};
+using tokeniser_gen_functor = std::function<const css_parser_token &(void)>;
+
}