diff --git a/libwccl/parser/grammar.g b/libwccl/parser/grammar.g
index 074020eeaefa442a181ce8036d414c1fc02e3f42..ca58421fa7cc28114830fd675af1ecda091e1f0a 100644
--- a/libwccl/parser/grammar.g
+++ b/libwccl/parser/grammar.g
@@ -295,15 +295,10 @@ parse_wccl_file
 	returns [boost::shared_ptr<WcclFile> wccl_file]
 {
 	wccl_file = boost::make_shared<WcclFile>(tagset, search_path);
-	boost::shared_ptr<TagRuleSequence> rule_seq;
 }
 	: (imports_section [*wccl_file])?
-	  (any_operator_section [*wccl_file] )*
-	  (
-		rule_seq = parse_tag_rule_sequence [tagset] { wccl_file->set_tag_rules(rule_seq); }
-		(any_operator_section [*wccl_file] )*
-	  )?
-	EOF
+	  (wccl_file_section [*wccl_file])+
+	  EOF
 ;
 
 
@@ -1900,6 +1895,48 @@ import [WcclFile& wccl_file]
 	}
 ;
 
+wccl_file_section [WcclFile& wccl_file]
+	: any_operator_section [wccl_file]
+	| tag_rules_section [wccl_file]
+	| match_rules_section [wccl_file]
+;
+
+tag_rules_section [WcclFile& wccl_file]
+{
+	boost::shared_ptr<TagRuleSequence> rule_seq;
+}
+	: rule_seq = parse_tag_rule_sequence [wccl_file.tagset()] {
+		if (wccl_file.has_tag_rules()) {
+			throw ParserException("Only one tag_rules section allowed in a WCCL file.");
+		}
+		wccl_file.set_tag_rules(rule_seq);
+	}
+;
+
+match_rules_section [WcclFile& wccl_file]
+{
+	ParsingScope scope(wccl_file);
+	boost::shared_ptr<MatchRule> match_rule;
+}
+	: "match_rules" {
+		if (wccl_file.has_match_rules()) {
+			throw ParserException("Only one match_rules section allowed in a WCCL file.");
+		}
+	}
+	LPAREN
+		match_rule = match_rule_operator [scope] {
+			wccl_file.add_match_rule(match_rule);
+			scope.reset_variables();
+		}
+		(
+			SEMI match_rule = match_rule_operator [scope] {
+				wccl_file.add_match_rule(match_rule);
+				scope.reset_variables();
+			}
+		)*
+	RPAREN
+;
+
 any_operator_section
 	[WcclFile& wccl_file]
 {
@@ -2117,11 +2154,12 @@ tag_rule_sequence
 	(
 		SEMI rle = tag_rule [scope] {
 			rule_seq->push_back(*rle);
+			scope.reset_variables();
 		}
 	)*
 ;
 
-// Temporary name. 
+// ----------------------------------------------------------------------------
 // This is wrapper for tag_rule_sequence in rules section in the wccl file
 tag_rules
 	[ParsingScope& scope]
diff --git a/libwccl/wcclfile.cpp b/libwccl/wcclfile.cpp
index 377018eac2942fa1233fa489cf27f53188458d86..4c6edb65264966196e26d4ae926559974b3efff3 100644
--- a/libwccl/wcclfile.cpp
+++ b/libwccl/wcclfile.cpp
@@ -50,6 +50,16 @@ std::ostream& WcclFile::write_to(std::ostream& os) const
 	if (has_tag_rules()) {
 		os << tag_rules_->to_string(tagset_) << '\n';
 	}
+	if (has_match_rules()) {
+		os << "match_rules(\n";
+		for (size_t i = 0; i < match_rules_.size(); ++i) {
+			if (i != 0) {
+				os << ";\n";
+			}
+			os << match_rules_[i]->to_string(tagset_);
+		}
+		os << "\n)\n";
+	}
 	return os;
 }
 
diff --git a/libwccl/wcclfile.h b/libwccl/wcclfile.h
index f287a813ba0d4c5cdb5e0e007d3277279526d70a..7d241973e17a6dc4f6a588725c9dd975d511c996 100644
--- a/libwccl/wcclfile.h
+++ b/libwccl/wcclfile.h
@@ -8,6 +8,7 @@
 #include <libwccl/values/tset.h>
 #include <libwccl/wcclfileopsections.h>
 #include <libwccl/ops/tagrulesequence.h>
+#include <libwccl/ops/matchrule.h>
 #include <libwccl/lexicon/lexicons.h>
 #include <libwccl/exception.h>
 #include <libpwrutils/pathsearch.h>
@@ -101,6 +102,10 @@ public:
 	boost::shared_ptr<TagRuleSequence> get_tag_rules_ptr();
 	boost::shared_ptr<const TagRuleSequence> get_tag_rules_ptr() const;
 
+	bool has_match_rules() const;
+	void add_match_rule(const boost::shared_ptr<MatchRule>& match_rule);
+	const std::vector<boost::shared_ptr<MatchRule> >& get_match_rules();
+
 	friend std::ostream& operator<<(std::ostream& ostream, const WcclFile& wccl_file);
 	std::string to_string() const;
 
@@ -112,6 +117,7 @@ private:
 	std::ostream& write_to(std::ostream& ostream) const;
 	std::vector<boost::shared_ptr<FunctionalOpSequence> > all_sections_;
 	boost::shared_ptr<TagRuleSequence> tag_rules_;
+	std::vector<boost::shared_ptr<MatchRule> > match_rules_;
 	boost::shared_ptr<Lexicons> lexicons_;
 	const Corpus2::Tagset& tagset_;
 	PwrNlp::PathSearcher<Wccl::FileNotFound> path_;
@@ -401,6 +407,24 @@ void WcclFile::set_tag_rules(const boost::shared_ptr<TagRuleSequence>& tag_rules
 	tag_rules_ = tag_rules;
 }
 
+inline
+bool WcclFile::has_match_rules() const
+{
+	return !match_rules_.empty();
+}
+
+inline
+void WcclFile::add_match_rule(const boost::shared_ptr<MatchRule>& match_rule)
+{
+	match_rules_.push_back(match_rule);
+}
+
+inline
+const std::vector<boost::shared_ptr<MatchRule> >& WcclFile::get_match_rules()
+{
+	return match_rules_;
+}
+
 inline
 std::ostream& operator <<(std::ostream& ostream, const WcclFile& wccl_file) {
 	return wccl_file.write_to(ostream);