[feaLib] Reject script dflt
and language DFLT
These are invalid casing variants of the frequently used `script DFLT` and `language dflt`. Adobe's makeotf tool does a similar check.
This commit is contained in:
parent
20392fb491
commit
86004df3b0
@ -166,7 +166,8 @@ class Parser(object):
|
||||
|
||||
def parse_language_(self):
|
||||
assert self.is_cur_keyword_("language")
|
||||
location, language = self.cur_token_location_, self.expect_tag_()
|
||||
location = self.cur_token_location_
|
||||
language = self.expect_language_tag_()
|
||||
include_default, required = (True, False)
|
||||
if self.next_token_ in {"exclude_dflt", "include_dflt"}:
|
||||
include_default = (self.expect_name_() == "include_dflt")
|
||||
@ -201,7 +202,7 @@ class Parser(object):
|
||||
|
||||
def parse_script_(self):
|
||||
assert self.is_cur_keyword_("script")
|
||||
location, script = self.cur_token_location_, self.expect_tag_()
|
||||
location, script = self.cur_token_location_, self.expect_script_tag_()
|
||||
self.expect_symbol_(";")
|
||||
return ast.ScriptStatement(location, script)
|
||||
|
||||
@ -294,7 +295,8 @@ class Parser(object):
|
||||
def parse_languagesystem_(self):
|
||||
assert self.cur_token_ == "languagesystem"
|
||||
location = self.cur_token_location_
|
||||
script, language = self.expect_tag_(), self.expect_tag_()
|
||||
script = self.expect_script_tag_()
|
||||
language = self.expect_language_tag_()
|
||||
self.expect_symbol_(";")
|
||||
if script == "DFLT" and language != "dflt":
|
||||
raise FeatureLibError(
|
||||
@ -371,6 +373,22 @@ class Parser(object):
|
||||
self.cur_token_location_)
|
||||
return (self.cur_token_ + " ")[:4]
|
||||
|
||||
def expect_script_tag_(self):
|
||||
tag = self.expect_tag_()
|
||||
if tag == "dflt":
|
||||
raise FeatureLibError(
|
||||
'"dflt" is not a valid script tag; use "DFLT" instead',
|
||||
self.cur_token_location_)
|
||||
return tag
|
||||
|
||||
def expect_language_tag_(self):
|
||||
tag = self.expect_tag_()
|
||||
if tag == "DFLT":
|
||||
raise FeatureLibError(
|
||||
'"DFLT" is not a valid language tag; use "dflt" instead',
|
||||
self.cur_token_location_)
|
||||
return tag
|
||||
|
||||
def expect_symbol_(self, symbol):
|
||||
self.advance_lexer_()
|
||||
if self.cur_token_type_ is Lexer.SYMBOL and self.cur_token_ == symbol:
|
||||
|
@ -199,6 +199,12 @@ class ParserTest(unittest.TestCase):
|
||||
self.assertTrue(s.include_default)
|
||||
self.assertTrue(s.required)
|
||||
|
||||
def test_language_DFLT(self):
|
||||
self.assertRaisesRegex(
|
||||
FeatureLibError,
|
||||
'"DFLT" is not a valid language tag; use "dflt" instead',
|
||||
self.parse, "feature test { language DFLT; } test;")
|
||||
|
||||
def test_lookup_block(self):
|
||||
[lookup] = self.parse("lookup Ligatures {} Ligatures;").statements
|
||||
self.assertEqual(lookup.name, "Ligatures")
|
||||
@ -256,6 +262,12 @@ class ParserTest(unittest.TestCase):
|
||||
self.assertEqual(type(s), ast.ScriptStatement)
|
||||
self.assertEqual(s.script, "cyrl")
|
||||
|
||||
def test_script_dflt(self):
|
||||
self.assertRaisesRegex(
|
||||
FeatureLibError,
|
||||
'"dflt" is not a valid script tag; use "DFLT" instead',
|
||||
self.parse, "feature test {script dflt;} test;")
|
||||
|
||||
def test_substitute_single_format_a(self): # GSUB LookupType 1
|
||||
doc = self.parse("feature smcp {substitute a by a.sc;} smcp;")
|
||||
sub = doc.statements[0].statements[0]
|
||||
@ -398,6 +410,14 @@ class ParserTest(unittest.TestCase):
|
||||
FeatureLibError,
|
||||
'For script "DFLT", the language must be "dflt"',
|
||||
self.parse, "languagesystem DFLT DEU;")
|
||||
self.assertRaisesRegex(
|
||||
FeatureLibError,
|
||||
'"dflt" is not a valid script tag; use "DFLT" instead',
|
||||
self.parse, "languagesystem dflt dflt;")
|
||||
self.assertRaisesRegex(
|
||||
FeatureLibError,
|
||||
'"DFLT" is not a valid language tag; use "dflt" instead',
|
||||
self.parse, "languagesystem latn DFLT;")
|
||||
self.assertRaisesRegex(
|
||||
FeatureLibError, "Expected ';'",
|
||||
self.parse, "languagesystem latn DEU")
|
||||
|
Loading…
x
Reference in New Issue
Block a user