2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								/*
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								 *  Copyright  ( c )  2020 - 2021 ,  Andreas  Kling  < kling @ serenityos . org > 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								 *  Copyright  ( c )  2021 ,  Linus  Groh  < linusg @ serenityos . org > 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								 *  Copyright  ( c )  2021 ,  Luke  Wilde  < lukew @ serenityos . org > 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								 *  Copyright  ( c )  2022 ,  Ali  Mohammad  Pur  < mpfard @ serenityos . org > 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								 * 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								 *  SPDX - License - Identifier :  BSD - 2 - Clause 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								 */ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# include  "IDLParser.h" 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# include  <AK/LexicalPath.h> 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# include  <AK/QuickSort.h> 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# include  <LibCore/File.h> 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								[[noreturn]]  static  void  report_parsing_error ( StringView  message ,  StringView  filename ,  StringView  input ,  size_t  offset )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    // FIXME: Spaghetti code ahead.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    size_t  lineno  =  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    size_t  colno  =  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    size_t  start_line  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    size_t  line_length  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    for  ( size_t  index  =  0 ;  index  <  input . length ( ) ;  + + index )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( offset  = =  index ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            colno  =  index  -  start_line  +  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( input [ index ]  = =  ' \n ' )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            if  ( index  > =  offset ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            start_line  =  index  +  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            line_length  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            + + lineno ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        }  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            + + line_length ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    StringBuilder  error_message ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    error_message . appendff ( " {} \n " ,  input . substring_view ( start_line ,  line_length ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    for  ( size_t  i  =  0 ;  i  <  colno  -  1 ;  + + i ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        error_message . append ( '   ' ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    error_message . append ( " \033 [1;31m^ \n " sv ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    error_message . appendff ( " {}:{}: error: {} \033 [0m \n " ,  filename ,  lineno ,  message ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    warnln ( " {} " ,  error_message . string_view ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    exit ( EXIT_FAILURE ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								static  String  convert_enumeration_value_to_cpp_enum_member ( String  const &  value ,  HashTable < String > &  names_already_seen )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    StringBuilder  builder ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    GenericLexer  lexer  {  value  } ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    while  ( ! lexer . is_eof ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        lexer . ignore_while ( [ ] ( auto  c )  {  return  is_ascii_space ( c )  | |  c  = =  ' - '  | |  c  = =  ' _ ' ;  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        auto  word  =  lexer . consume_while ( [ ] ( auto  c )  {  return  is_ascii_alphanumeric ( c ) ;  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( ! word . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            builder . append ( word . to_titlecase_string ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        }  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            auto  non_alnum_string  =  lexer . consume_while ( [ ] ( auto  c )  {  return  ! is_ascii_alphanumeric ( c ) ;  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            if  ( ! non_alnum_string . is_empty ( ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 20:10:18 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								                builder . append ( ' _ ' ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( builder . is_empty ( ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        builder . append ( " Empty " sv ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    while  ( names_already_seen . contains ( builder . string_view ( ) ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        builder . append ( ' _ ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    names_already_seen . set ( builder . string_view ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    return  builder . build ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								namespace  IDL  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								HashTable < NonnullOwnPtr < Interface > >  Parser : : s_interfaces  { } ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								HashMap < String ,  Interface * >  Parser : : s_resolved_imports  { } ;  
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Parser : : assert_specific ( char  ch )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( ! lexer . consume_specific ( ch ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        report_parsing_error ( String : : formatted ( " expected '{}' " ,  ch ) ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Parser : : consume_whitespace ( )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    bool  consumed  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    while  ( consumed )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        consumed  =  lexer . consume_while ( is_ascii_space ) . length ( )  >  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( lexer . consume_specific ( " // " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            lexer . consume_until ( ' \n ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            lexer . ignore ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            consumed  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Parser : : assert_string ( StringView  expected )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( ! lexer . consume_specific ( expected ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        report_parsing_error ( String : : formatted ( " expected '{}' " ,  expected ) ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								HashMap < String ,  String >  Parser : : parse_extended_attributes ( )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    HashMap < String ,  String >  extended_attributes ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    for  ( ; ; )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( lexer . consume_specific ( ' ] ' ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        auto  name  =  lexer . consume_until ( [ ] ( auto  ch )  {  return  ch  = =  ' ] '  | |  ch  = =  ' = '  | |  ch  = =  ' , ' ;  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( lexer . consume_specific ( ' = ' ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            auto  value  =  lexer . consume_until ( [ ] ( auto  ch )  {  return  ch  = =  ' ] '  | |  ch  = =  ' , ' ;  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            extended_attributes . set ( name ,  value ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        }  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            extended_attributes . set ( name ,  { } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        lexer . consume_specific ( ' , ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    return  extended_attributes ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-01 21:43:02 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								static  HashTable < String >  import_stack ;  
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Optional < Interface & >  Parser : : resolve_import ( auto  path )  
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  include_path  =  LexicalPath : : join ( import_base_path ,  path ) . string ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( ! Core : : File : : exists ( include_path ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        report_parsing_error ( String : : formatted ( " {}: No such file or directory " ,  include_path ) ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  real_path  =  Core : : File : : real_path_for ( include_path ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-01 21:43:02 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    if  ( s_resolved_imports . contains ( real_path ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        return  * s_resolved_imports . find ( real_path ) - > value ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-01 21:43:02 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    if  ( import_stack . contains ( real_path ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        report_parsing_error ( String : : formatted ( " Circular import detected: {} " ,  include_path ) ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    import_stack . set ( real_path ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  file_or_error  =  Core : : File : : open ( real_path ,  Core : : OpenMode : : ReadOnly ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( file_or_error . is_error ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        report_parsing_error ( String : : formatted ( " Failed to open {}: {} " ,  real_path ,  file_or_error . error ( ) ) ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  data  =  file_or_error . value ( ) - > read_all ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    auto &  result  =  Parser ( real_path ,  data ,  import_base_path ) . parse ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-01 21:43:02 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    import_stack . remove ( real_path ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    s_resolved_imports . set ( real_path ,  & result ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-30 23:30:12 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    return  result ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								NonnullRefPtr < Type >  Parser : : parse_type ( )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( lexer . consume_specific ( ' ( ' ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        NonnullRefPtrVector < Type >  union_member_types ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        union_member_types . append ( parse_type ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        consume_whitespace ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        assert_string ( " or " sv ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        union_member_types . append ( parse_type ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        while  ( lexer . consume_specific ( " or " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            union_member_types . append ( parse_type ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        assert_specific ( ' ) ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        bool  nullable  =  lexer . consume_specific ( ' ? ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        return  adopt_ref ( * new  UnionType ( " " ,  nullable ,  move ( union_member_types ) ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    bool  unsigned_  =  lexer . consume_specific ( " unsigned " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( unsigned_ ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  name  =  lexer . consume_until ( [ ] ( auto  ch )  {  return  ! is_ascii_alphanumeric ( ch )  & &  ch  ! =  ' _ ' ;  } ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-05-09 22:25:42 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( name . equals_ignoring_case ( " long " sv ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( lexer . consume_specific ( " long " sv ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            name  =  " long long " sv ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-05-09 22:25:42 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    NonnullRefPtrVector < Type >  parameters ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    bool  is_parameterized_type  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( lexer . consume_specific ( ' < ' ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        is_parameterized_type  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        parameters . append ( parse_type ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        while  ( lexer . consume_specific ( ' , ' ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            parameters . append ( parse_type ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        lexer . consume_specific ( ' > ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  nullable  =  lexer . consume_specific ( ' ? ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    StringBuilder  builder ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( unsigned_ ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        builder . append ( " unsigned  " sv ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    builder . append ( name ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( is_parameterized_type ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        return  adopt_ref ( * new  ParameterizedType ( builder . to_string ( ) ,  nullable ,  move ( parameters ) ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    return  adopt_ref ( * new  Type ( builder . to_string ( ) ,  nullable ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Parser : : parse_attribute ( HashMap < String ,  String > &  extended_attributes ,  Interface &  interface )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    bool  readonly  =  lexer . consume_specific ( " readonly " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( readonly ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( lexer . consume_specific ( " attribute " ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  type  =  parse_type ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  name  =  lexer . consume_until ( [ ] ( auto  ch )  {  return  is_ascii_space ( ch )  | |  ch  = =  ' ; ' ;  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    assert_specific ( ' ; ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  name_as_string  =  name . to_string ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  getter_callback_name  =  String : : formatted ( " {}_getter " ,  name_as_string . to_snakecase ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  setter_callback_name  =  String : : formatted ( " {}_setter " ,  name_as_string . to_snakecase ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    Attribute  attribute  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        readonly , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        move ( type ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        move ( name_as_string ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        move ( extended_attributes ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        move ( getter_callback_name ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        move ( setter_callback_name ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    interface . attributes . append ( move ( attribute ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Parser : : parse_constant ( Interface &  interface )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    lexer . consume_specific ( " const " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  type  =  parse_type ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  name  =  lexer . consume_until ( [ ] ( auto  ch )  {  return  is_ascii_space ( ch )  | |  ch  = =  ' = ' ;  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    lexer . consume_specific ( ' = ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  value  =  lexer . consume_while ( [ ] ( auto  ch )  {  return  ! is_ascii_space ( ch )  & &  ch  ! =  ' ; ' ;  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    assert_specific ( ' ; ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    Constant  constant  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        move ( type ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        move ( name ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        move ( value ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    interface . constants . append ( move ( constant ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								Vector < Parameter >  Parser : : parse_parameters ( )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    Vector < Parameter >  parameters ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    for  ( ; ; )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( lexer . next_is ( ' ) ' ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        HashMap < String ,  String >  extended_attributes ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( lexer . consume_specific ( ' [ ' ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            extended_attributes  =  parse_extended_attributes ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        bool  optional  =  lexer . consume_specific ( " optional " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( optional ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        auto  type  =  parse_type ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        bool  variadic  =  lexer . consume_specific ( " ... " sv ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        auto  name  =  lexer . consume_until ( [ ] ( auto  ch )  {  return  is_ascii_space ( ch )  | |  ch  = =  ' , '  | |  ch  = =  ' ) '  | |  ch  = =  ' = ' ;  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        Parameter  parameter  =  {  move ( type ) ,  move ( name ) ,  optional ,  { } ,  extended_attributes ,  variadic  } ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( variadic )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            // Variadic parameters must be last and do not have default values.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            parameters . append ( move ( parameter ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( lexer . next_is ( ' ) ' ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            parameters . append ( move ( parameter ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( lexer . next_is ( ' = ' )  & &  optional )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            assert_specific ( ' = ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            auto  default_value  =  lexer . consume_until ( [ ] ( auto  ch )  {  return  is_ascii_space ( ch )  | |  ch  = =  ' , '  | |  ch  = =  ' ) ' ;  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            parameter . optional_default_value  =  default_value ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        parameters . append ( move ( parameter ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( lexer . next_is ( ' ) ' ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        assert_specific ( ' , ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    return  parameters ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								Function  Parser : : parse_function ( HashMap < String ,  String > &  extended_attributes ,  Interface &  interface ,  IsSpecialOperation  is_special_operation )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    bool  static_  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( lexer . consume_specific ( " static " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        static_  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  return_type  =  parse_type ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  name  =  lexer . consume_until ( [ ] ( auto  ch )  {  return  is_ascii_space ( ch )  | |  ch  = =  ' ( ' ;  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    assert_specific ( ' ( ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  parameters  =  parse_parameters ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    assert_specific ( ' ) ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    assert_specific ( ' ; ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-03-05 20:51:17 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    Function  function  {  move ( return_type ) ,  name ,  move ( parameters ) ,  move ( extended_attributes ) ,  { } ,  false  } ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    // "Defining a special operation with an identifier is equivalent to separating the special operation out into its own declaration without an identifier."
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( is_special_operation  = =  IsSpecialOperation : : No  | |  ( is_special_operation  = =  IsSpecialOperation : : Yes  & &  ! name . is_empty ( ) ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( ! static_ ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            interface . functions . append ( function ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        else 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            interface . static_functions . append ( function ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    return  function ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Parser : : parse_constructor ( Interface &  interface )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    assert_string ( " constructor " sv ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    assert_specific ( ' ( ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  parameters  =  parse_parameters ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    assert_specific ( ' ) ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    assert_specific ( ' ; ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    interface . constructors . append ( Constructor  {  interface . name ,  move ( parameters )  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Parser : : parse_stringifier ( HashMap < String ,  String > &  extended_attributes ,  Interface &  interface )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    assert_string ( " stringifier " sv ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    interface . has_stringifier  =  true ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    if  ( lexer . next_is ( " readonly " sv )  | |  lexer . next_is ( " attribute " sv ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        parse_attribute ( extended_attributes ,  interface ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        interface . stringifier_attribute  =  interface . attributes . last ( ) . name ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    }  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        assert_specific ( ' ; ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Parser : : parse_iterable ( Interface &  interface )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    assert_string ( " iterable " sv ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    assert_specific ( ' < ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  first_type  =  parse_type ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( lexer . next_is ( ' , ' ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( interface . supports_indexed_properties ( ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            report_parsing_error ( " Interfaces with a pair iterator must not supported indexed properties. " sv ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        assert_specific ( ' , ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        auto  second_type  =  parse_type ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        interface . pair_iterator_types  =  Tuple  {  move ( first_type ) ,  move ( second_type )  } ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    }  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( ! interface . supports_indexed_properties ( ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            report_parsing_error ( " Interfaces with a value iterator must supported indexed properties. " sv ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        interface . value_iterator_type  =  move ( first_type ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    assert_specific ( ' > ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    assert_specific ( ' ; ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Parser : : parse_getter ( HashMap < String ,  String > &  extended_attributes ,  Interface &  interface )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    assert_string ( " getter " sv ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  function  =  parse_function ( extended_attributes ,  interface ,  IsSpecialOperation : : Yes ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( function . parameters . size ( )  ! =  1 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        report_parsing_error ( String : : formatted ( " Named/indexed property getters must have only 1 parameter, got {} parameters. " ,  function . parameters . size ( ) ) ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto &  identifier  =  function . parameters . first ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( identifier . type - > nullable ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        report_parsing_error ( " identifier's type must not be nullable. " sv ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( identifier . optional ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        report_parsing_error ( " identifier must not be optional. " sv ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    // FIXME: Disallow variadic functions once they're supported.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( identifier . type - > name  = =  " DOMString " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( interface . named_property_getter . has_value ( ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            report_parsing_error ( " An interface can only have one named property getter. " sv ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        interface . named_property_getter  =  move ( function ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    }  else  if  ( identifier . type - > name  = =  " unsigned long " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( interface . indexed_property_getter . has_value ( ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            report_parsing_error ( " An interface can only have one indexed property getter. " sv ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        interface . indexed_property_getter  =  move ( function ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    }  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        report_parsing_error ( String : : formatted ( " Named/indexed property getter's identifier's type must be either 'DOMString' or 'unsigned long', got '{}'. " ,  identifier . type - > name ) ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Parser : : parse_setter ( HashMap < String ,  String > &  extended_attributes ,  Interface &  interface )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    assert_string ( " setter " sv ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  function  =  parse_function ( extended_attributes ,  interface ,  IsSpecialOperation : : Yes ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( function . parameters . size ( )  ! =  2 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        report_parsing_error ( String : : formatted ( " Named/indexed property setters must have only 2 parameters, got {} parameter(s). " ,  function . parameters . size ( ) ) ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto &  identifier  =  function . parameters . first ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( identifier . type - > nullable ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        report_parsing_error ( " identifier's type must not be nullable. " sv ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( identifier . optional ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        report_parsing_error ( " identifier must not be optional. " sv ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    // FIXME: Disallow variadic functions once they're supported.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( identifier . type - > name  = =  " DOMString " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( interface . named_property_setter . has_value ( ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            report_parsing_error ( " An interface can only have one named property setter. " sv ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( ! interface . named_property_getter . has_value ( ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            report_parsing_error ( " A named property setter must be accompanied by a named property getter. " sv ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        interface . named_property_setter  =  move ( function ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    }  else  if  ( identifier . type - > name  = =  " unsigned long " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( interface . indexed_property_setter . has_value ( ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            report_parsing_error ( " An interface can only have one indexed property setter. " sv ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( ! interface . indexed_property_getter . has_value ( ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            report_parsing_error ( " An indexed property setter must be accompanied by an indexed property getter. " sv ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        interface . indexed_property_setter  =  move ( function ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    }  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        report_parsing_error ( String : : formatted ( " Named/indexed property setter's identifier's type must be either 'DOMString' or 'unsigned long', got '{}'. " ,  identifier . type - > name ) ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Parser : : parse_deleter ( HashMap < String ,  String > &  extended_attributes ,  Interface &  interface )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    assert_string ( " deleter " sv ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  function  =  parse_function ( extended_attributes ,  interface ,  IsSpecialOperation : : Yes ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( function . parameters . size ( )  ! =  1 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        report_parsing_error ( String : : formatted ( " Named property deleter must have only 1 parameter, got {} parameters. " ,  function . parameters . size ( ) ) ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto &  identifier  =  function . parameters . first ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( identifier . type - > nullable ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        report_parsing_error ( " identifier's type must not be nullable. " sv ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( identifier . optional ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        report_parsing_error ( " identifier must not be optional. " sv ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    // FIXME: Disallow variadic functions once they're supported.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( identifier . type - > name  = =  " DOMString " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( interface . named_property_deleter . has_value ( ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            report_parsing_error ( " An interface can only have one named property deleter. " sv ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( ! interface . named_property_getter . has_value ( ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            report_parsing_error ( " A named property deleter must be accompanied by a named property getter. " sv ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        interface . named_property_deleter  =  move ( function ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    }  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        report_parsing_error ( String : : formatted ( " Named property deleter's identifier's type must be 'DOMString', got '{}'. " ,  identifier . type - > name ) ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Parser : : parse_interface ( Interface &  interface )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    interface . name  =  lexer . consume_until ( [ ] ( auto  ch )  {  return  is_ascii_space ( ch ) ;  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( lexer . consume_specific ( ' : ' ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        interface . parent_name  =  lexer . consume_until ( [ ] ( auto  ch )  {  return  is_ascii_space ( ch ) ;  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    assert_specific ( ' { ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    for  ( ; ; )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        HashMap < String ,  String >  extended_attributes ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( lexer . consume_specific ( ' } ' ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            assert_specific ( ' ; ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( lexer . consume_specific ( ' [ ' ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            extended_attributes  =  parse_extended_attributes ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            if  ( ! interface . has_unscopable_member  & &  extended_attributes . contains ( " Unscopable " ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                interface . has_unscopable_member  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( lexer . next_is ( " constructor " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            parse_constructor ( interface ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( lexer . next_is ( " const " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            parse_constant ( interface ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( lexer . next_is ( " stringifier " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            parse_stringifier ( extended_attributes ,  interface ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( lexer . next_is ( " iterable " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            parse_iterable ( interface ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( lexer . next_is ( " readonly " )  | |  lexer . next_is ( " attribute " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            parse_attribute ( extended_attributes ,  interface ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( lexer . next_is ( " getter " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            parse_getter ( extended_attributes ,  interface ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( lexer . next_is ( " setter " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            parse_setter ( extended_attributes ,  interface ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( lexer . next_is ( " deleter " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            parse_deleter ( extended_attributes ,  interface ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        parse_function ( extended_attributes ,  interface ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    interface . wrapper_class  =  String : : formatted ( " {}Wrapper " ,  interface . name ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    interface . wrapper_base_class  =  String : : formatted ( " {}Wrapper " ,  interface . parent_name . is_empty ( )  ?  String : : empty ( )  :  interface . parent_name ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    interface . constructor_class  =  String : : formatted ( " {}Constructor " ,  interface . name ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    interface . prototype_class  =  String : : formatted ( " {}Prototype " ,  interface . name ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    interface . prototype_base_class  =  String : : formatted ( " {}Prototype " ,  interface . parent_name . is_empty ( )  ?  " Object "  :  interface . parent_name ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Parser : : parse_enumeration ( Interface &  interface )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    assert_string ( " enum " sv ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    Enumeration  enumeration  { } ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  name  =  lexer . consume_until ( [ ] ( auto  ch )  {  return  is_ascii_space ( ch ) ;  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    assert_specific ( ' { ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    bool  first  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    for  ( ;  ! lexer . is_eof ( ) ; )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( lexer . next_is ( ' } ' ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( ! first )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            assert_specific ( ' , ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        assert_specific ( ' " ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        auto  string  =  lexer . consume_until ( ' " ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        assert_specific ( ' " ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( enumeration . values . contains ( string ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            report_parsing_error ( String : : formatted ( " Enumeration {} contains duplicate member '{}' " ,  name ,  string ) ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        else 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            enumeration . values . set ( string ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( first ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            enumeration . first_member  =  move ( string ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        first  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    assert_specific ( ' } ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    assert_specific ( ' ; ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    HashTable < String >  names_already_seen ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    for  ( auto &  entry  :  enumeration . values ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        enumeration . translated_cpp_names . set ( entry ,  convert_enumeration_value_to_cpp_enum_member ( entry ,  names_already_seen ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    interface . enumerations . set ( name ,  move ( enumeration ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-03-30 23:32:44 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Parser : : parse_typedef ( Interface &  interface )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    assert_string ( " typedef " sv ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-30 23:32:44 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    HashMap < String ,  String >  extended_attributes ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( lexer . consume_specific ( ' [ ' ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        extended_attributes  =  parse_extended_attributes ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  type  =  parse_type ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  name  =  lexer . consume_until ( ' ; ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    assert_specific ( ' ; ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    interface . typedefs . set ( name ,  Typedef  {  move ( extended_attributes ) ,  move ( type )  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								void  Parser : : parse_dictionary ( Interface &  interface )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    assert_string ( " dictionary " sv ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    Dictionary  dictionary  { } ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  name  =  lexer . consume_until ( [ ] ( auto  ch )  {  return  is_ascii_space ( ch ) ;  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( lexer . consume_specific ( ' : ' ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        dictionary . parent_name  =  lexer . consume_until ( [ ] ( auto  ch )  {  return  is_ascii_space ( ch ) ;  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    assert_specific ( ' { ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    for  ( ; ; )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( lexer . consume_specific ( ' } ' ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            assert_specific ( ' ; ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        bool  required  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        HashMap < String ,  String >  extended_attributes ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( lexer . consume_specific ( " required " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            required  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            if  ( lexer . consume_specific ( ' [ ' ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                extended_attributes  =  parse_extended_attributes ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        auto  type  =  parse_type ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        auto  name  =  lexer . consume_until ( [ ] ( auto  ch )  {  return  is_ascii_space ( ch )  | |  ch  = =  ' ; ' ;  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        Optional < StringView >  default_value ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( lexer . consume_specific ( ' = ' ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            VERIFY ( ! required ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            default_value  =  lexer . consume_until ( [ ] ( auto  ch )  {  return  is_ascii_space ( ch )  | |  ch  = =  ' ; ' ;  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        assert_specific ( ' ; ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        DictionaryMember  member  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            required , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            move ( type ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            name , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            move ( extended_attributes ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            Optional < String > ( move ( default_value ) ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        dictionary . members . append ( move ( member ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    // dictionary members need to be evaluated in lexicographical order
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    quick_sort ( dictionary . members ,  [ & ] ( auto &  one ,  auto &  two )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        return  one . name  <  two . name ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    interface . dictionaries . set ( name ,  move ( dictionary ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 03:15:57 +03:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Parser : : parse_interface_mixin ( Interface &  interface )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    auto  mixin_interface_ptr  =  make < Interface > ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto &  mixin_interface  =  * mixin_interface_ptr ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    VERIFY ( s_interfaces . set ( move ( mixin_interface_ptr ) )  = =  AK : : HashSetResult : : InsertedNewEntry ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    mixin_interface . module_own_path  =  interface . module_own_path ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    mixin_interface . is_mixin  =  true ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 03:15:57 +03:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    assert_string ( " interface " sv ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 03:15:57 +03:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    assert_string ( " mixin " sv ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 03:15:57 +03:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    auto  offset  =  lexer . tell ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    parse_interface ( mixin_interface ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( ! mixin_interface . parent_name . is_empty ( ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        report_parsing_error ( " Mixin interfaces are not allowed to have inherited parents " sv ,  filename ,  input ,  offset ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 03:15:57 +03:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    auto  name  =  mixin_interface . name ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    interface . mixins . set ( move ( name ) ,  & mixin_interface ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 03:15:57 +03:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-03-30 23:35:13 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Parser : : parse_callback_function ( HashMap < String ,  String > &  extended_attributes ,  Interface &  interface )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    assert_string ( " callback " sv ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-30 23:35:13 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  name  =  lexer . consume_until ( [ ] ( auto  ch )  {  return  is_ascii_space ( ch ) ;  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    assert_specific ( ' = ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  return_type  =  parse_type ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    assert_specific ( ' ( ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  parameters  =  parse_parameters ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    assert_specific ( ' ) ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    assert_specific ( ' ; ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    interface . callback_functions . set ( name ,  CallbackFunction  {  move ( return_type ) ,  move ( parameters ) ,  extended_attributes . contains ( " LegacyTreatNonObjectAsNull " )  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								void  Parser : : parse_non_interface_entities ( bool  allow_interface ,  Interface &  interface )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    while  ( ! lexer . is_eof ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-30 23:34:12 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        HashMap < String ,  String >  extended_attributes ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( lexer . consume_specific ( ' [ ' ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            extended_attributes  =  parse_extended_attributes ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        if  ( lexer . next_is ( " dictionary " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            parse_dictionary ( interface ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        }  else  if  ( lexer . next_is ( " enum " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            parse_enumeration ( interface ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-30 23:32:44 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        }  else  if  ( lexer . next_is ( " typedef " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            parse_typedef ( interface ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 03:15:57 +03:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        }  else  if  ( lexer . next_is ( " interface mixin " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            parse_interface_mixin ( interface ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-30 23:35:13 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        }  else  if  ( lexer . next_is ( " callback " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            parse_callback_function ( extended_attributes ,  interface ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        }  else  if  ( ( allow_interface  & &  ! lexer . next_is ( " interface " ) )  | |  ! allow_interface )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 03:15:57 +03:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            auto  current_offset  =  lexer . tell ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            auto  name  =  lexer . consume_until ( [ ] ( auto  ch )  {  return  is_ascii_space ( ch ) ;  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            if  ( lexer . consume_specific ( " includes " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                auto  mixin_name  =  lexer . consume_until ( [ ] ( auto  ch )  {  return  is_ascii_space ( ch )  | |  ch  = =  ' ; ' ;  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                interface . included_mixins . ensure ( name ) . set ( mixin_name ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                assert_specific ( ' ; ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            }  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-11 17:32:29 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								                report_parsing_error ( " expected 'enum' or 'dictionary' " sv ,  filename ,  input ,  current_offset ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 03:15:57 +03:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            } 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        }  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-30 23:34:12 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            interface . extended_attributes  =  move ( extended_attributes ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-03-30 23:32:44 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  resolve_typedef ( Interface &  interface ,  NonnullRefPtr < Type > &  type ,  HashMap < String ,  String > *  extended_attributes  =  { } )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( is < ParameterizedType > ( * type ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        auto  parameterized_type  =  static_ptr_cast < ParameterizedType > ( type ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        auto &  parameters  =  static_cast < Vector < NonnullRefPtr < Type > > & > ( parameterized_type - > parameters ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        for  ( auto &  parameter  :  parameters ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            resolve_typedef ( interface ,  parameter ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  it  =  interface . typedefs . find ( type - > name ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( it  = =  interface . typedefs . end ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        return ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-06-04 03:59:51 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    bool  is_nullable  =  type - > nullable ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-30 23:32:44 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    type  =  it - > value . type ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-06-04 03:59:51 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    type - > nullable  =  is_nullable ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-30 23:32:44 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    if  ( ! extended_attributes ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    for  ( auto &  attribute  :  it - > value . extended_attributes ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        extended_attributes - > set ( attribute . key ,  attribute . value ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  resolve_parameters_typedefs ( Interface &  interface ,  Vector < Parameter > &  parameters )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    for  ( auto &  parameter  :  parameters ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        resolve_typedef ( interface ,  parameter . type ,  & parameter . extended_attributes ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								template < typename  FunctionType >  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  resolve_function_typedefs ( Interface &  interface ,  FunctionType &  function )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    resolve_typedef ( interface ,  function . return_type ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    resolve_parameters_typedefs ( interface ,  function . parameters ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Interface &  Parser : : parse ( )  
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto  this_module  =  Core : : File : : real_path_for ( filename ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    auto  interface_ptr  =  make < Interface > ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    auto &  interface  =  * interface_ptr ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    VERIFY ( s_interfaces . set ( move ( interface_ptr ) )  = =  AK : : HashSetResult : : InsertedNewEntry ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    interface . module_own_path  =  this_module ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    s_resolved_imports . set ( this_module ,  & interface ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    Vector < Interface & >  imports ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    HashTable < String >  required_imported_paths ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    while  ( lexer . consume_specific ( " #import " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        assert_specific ( ' < ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        auto  path  =  lexer . consume_until ( ' > ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        lexer . ignore ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        auto  maybe_interface  =  resolve_import ( path ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( maybe_interface . has_value ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            for  ( auto &  entry  :  maybe_interface . value ( ) . required_imported_paths ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-30 23:30:12 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								                required_imported_paths . set ( entry ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            imports . append ( maybe_interface . release_value ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        consume_whitespace ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    interface . required_imported_paths  =  required_imported_paths ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    parse_non_interface_entities ( true ,  interface ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( lexer . consume_specific ( " interface " ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        parse_interface ( interface ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    parse_non_interface_entities ( false ,  interface ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    for  ( auto &  import  :  imports )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        // FIXME: Instead of copying every imported entity into the current interface, query imports directly
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        for  ( auto &  dictionary  :  import . dictionaries ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            interface . dictionaries . set ( dictionary . key ,  dictionary . value ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        for  ( auto &  enumeration  :  import . enumerations )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            auto  enumeration_copy  =  enumeration . value ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            enumeration_copy . is_original_definition  =  false ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            interface . enumerations . set ( enumeration . key ,  move ( enumeration_copy ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 03:15:57 +03:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-03-30 23:32:44 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        for  ( auto &  typedef_  :  import . typedefs ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            interface . typedefs . set ( typedef_ . key ,  typedef_ . value ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-30 23:32:44 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 03:15:57 +03:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        for  ( auto &  mixin  :  import . mixins )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            if  ( auto  it  =  interface . mixins . find ( mixin . key ) ;  it  ! =  interface . mixins . end ( )  & &  it - > value  ! =  mixin . value ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 03:15:57 +03:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								                report_parsing_error ( String : : formatted ( " Mixin '{}' was already defined in {} " ,  mixin . key ,  mixin . value - > module_own_path ) ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            interface . mixins . set ( mixin . key ,  mixin . value ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 03:15:57 +03:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-30 23:35:13 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        for  ( auto &  callback_function  :  import . callback_functions ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            interface . callback_functions . set ( callback_function . key ,  callback_function . value ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 03:15:57 +03:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    // Resolve mixins
 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    if  ( auto  it  =  interface . included_mixins . find ( interface . name ) ;  it  ! =  interface . included_mixins . end ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 03:15:57 +03:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        for  ( auto &  entry  :  it - > value )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            auto  mixin_it  =  interface . mixins . find ( entry ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            if  ( mixin_it  = =  interface . mixins . end ( ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 03:15:57 +03:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								                report_parsing_error ( String : : formatted ( " Mixin '{}' was never defined " ,  entry ) ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            auto &  mixin  =  mixin_it - > value ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            interface . attributes . extend ( mixin - > attributes ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            interface . constants . extend ( mixin - > constants ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            interface . functions . extend ( mixin - > functions ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            interface . static_functions . extend ( mixin - > static_functions ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            if  ( interface . has_stringifier  & &  mixin - > has_stringifier ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                report_parsing_error ( String : : formatted ( " Both interface '{}' and mixin '{}' have defined stringifier attributes " ,  interface . name ,  mixin - > name ) ,  filename ,  input ,  lexer . tell ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 03:15:57 +03:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            if  ( mixin - > has_stringifier )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								                interface . stringifier_attribute  =  mixin - > stringifier_attribute ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                interface . has_stringifier  =  true ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 03:15:57 +03:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-03-30 23:32:44 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    // Resolve typedefs
 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    for  ( auto &  attribute  :  interface . attributes ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        resolve_typedef ( interface ,  attribute . type ,  & attribute . extended_attributes ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    for  ( auto &  constant  :  interface . constants ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        resolve_typedef ( interface ,  constant . type ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    for  ( auto &  constructor  :  interface . constructors ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        resolve_parameters_typedefs ( interface ,  constructor . parameters ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    for  ( auto &  function  :  interface . functions ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        resolve_function_typedefs ( interface ,  function ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    for  ( auto &  static_function  :  interface . static_functions ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        resolve_function_typedefs ( interface ,  static_function ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( interface . value_iterator_type . has_value ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        resolve_typedef ( interface ,  * interface . value_iterator_type ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( interface . pair_iterator_types . has_value ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        resolve_typedef ( interface ,  interface . pair_iterator_types - > get < 0 > ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        resolve_typedef ( interface ,  interface . pair_iterator_types - > get < 1 > ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-30 23:32:44 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    if  ( interface . named_property_getter . has_value ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        resolve_function_typedefs ( interface ,  * interface . named_property_getter ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( interface . named_property_setter . has_value ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        resolve_function_typedefs ( interface ,  * interface . named_property_setter ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( interface . indexed_property_getter . has_value ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        resolve_function_typedefs ( interface ,  * interface . indexed_property_getter ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( interface . indexed_property_setter . has_value ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        resolve_function_typedefs ( interface ,  * interface . indexed_property_setter ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( interface . named_property_deleter . has_value ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        resolve_function_typedefs ( interface ,  * interface . named_property_deleter ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( interface . named_property_getter . has_value ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        resolve_function_typedefs ( interface ,  * interface . named_property_getter ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    for  ( auto &  dictionary  :  interface . dictionaries )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-30 23:32:44 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        for  ( auto &  dictionary_member  :  dictionary . value . members ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            resolve_typedef ( interface ,  dictionary_member . type ,  & dictionary_member . extended_attributes ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-30 23:32:44 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    for  ( auto &  callback_function  :  interface . callback_functions ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        resolve_function_typedefs ( interface ,  callback_function . value ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-30 23:32:44 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-03-05 20:51:17 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    // Create overload sets
 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    for  ( auto &  function  :  interface . functions )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        auto &  overload_set  =  interface . overload_sets . ensure ( function . name ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-05 20:51:17 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        function . overload_index  =  overload_set . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        overload_set . append ( function ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    for  ( auto &  overload_set  :  interface . overload_sets )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-05 20:51:17 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        if  ( overload_set . value . size ( )  = =  1 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        for  ( auto &  overloaded_function  :  overload_set . value ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            overloaded_function . is_overloaded  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    for  ( auto &  function  :  interface . static_functions )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        auto &  overload_set  =  interface . static_overload_sets . ensure ( function . name ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-05 20:51:17 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        function . overload_index  =  overload_set . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        overload_set . append ( function ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    for  ( auto &  overload_set  :  interface . static_overload_sets )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-05 20:51:17 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        if  ( overload_set . value . size ( )  = =  1 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        for  ( auto &  overloaded_function  :  overload_set . value ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            overloaded_function . is_overloaded  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    // FIXME: Add support for overloading constructors
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-30 19:27:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    if  ( interface . will_generate_code ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        interface . required_imported_paths . set ( this_module ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    interface . imported_modules  =  move ( imports ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-17 02:00:43 +03:30 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    return  interface ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								Parser : : Parser ( String  filename ,  StringView  contents ,  String  import_base_path )  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    :  import_base_path ( move ( import_base_path ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    ,  filename ( move ( filename ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    ,  input ( contents ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    ,  lexer ( input ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}