* reworked saving/restoring the scanner state (immediately replace scanner

with temporary one when saving, since it's also freed when restoring ->
    called replace_scanner() instead of save_scanner() now)
  * when using -vd, print out the text that is internally generated for
    injecting into the scanner

git-svn-id: branches/jvmbackend@18442 -
This commit is contained in:
Jonas Maebe 2011-08-20 07:59:54 +00:00
parent 698deb08c5
commit 009a30d8cf
4 changed files with 389 additions and 374 deletions

View File

@ -375,7 +375,7 @@ scanner_e_illegal_alignment_directive=02088_E_Illegal alignment directive
#
# Parser
#
# 03317 is the last used one
# 03318 is the last used one
#
% \section{Parser messages}
% This section lists all parser messages. The parser takes care of the
@ -1416,6 +1416,10 @@ parser_e_java_no_inherited_constructor=03317_E_Constructors are not automaticall
% For compatibility with external Java code, FPC does the same. If you require access to the same
% constructors in a child class, define them in the child class and call the inherited one from
% there.
parser_d_internal_parser_string=03318_D_Parsing internally generated code: $1
% The compiler sometimes internally constructs Pascal code that is subsequently
% injected into the program. These messages display such code, in order to help
% with debugging errors in them.
% \end{description}
# Type Checking
#

View File

@ -409,6 +409,7 @@ const
parser_e_final_only_external=03315;
parser_e_no_typed_const=03316;
parser_e_java_no_inherited_constructor=03317;
parser_d_internal_parser_string=03318;
type_e_mismatch=04000;
type_e_incompatible_types=04001;
type_e_not_equal_types=04002;
@ -908,9 +909,9 @@ const
option_info=11024;
option_help_pages=11025;
MsgTxtSize = 61683;
MsgTxtSize = 61729;
MsgIdxMax : array[1..20] of longint=(
26,89,318,105,87,54,111,23,202,63,
26,89,319,105,87,54,111,23,202,63,
49,20,1,1,1,1,1,1,1,1
);

File diff suppressed because it is too large Load Diff

View File

@ -27,35 +27,9 @@ unit symcreat;
interface
uses
finput,
finput,tokens,scanner,
symconst,symdef,symbase;
{ in the JVM, constructors are not automatically inherited (so you can hide
them). To emulate the Pascal behaviour, we have to automatically add
all parent constructors to the current class as well. }
procedure add_missing_parent_constructors_intf(obj: tobjectdef);
procedure add_missing_parent_constructors_impl(obj: tobjectdef);
{ parses a (class or regular) method/constructor/destructor declaration from
str, as if it were declared in astruct's declaration body }
function str_parse_method_dec(str: ansistring; is_classdef: boolean; astruct: tabstractrecorddef; out pd: tprocdef): boolean;
{ parses a (class or regular) method/constructor/destructor implementation
from str, as if it appeared in the current unit's implementation section }
function str_parse_method_impl(str: ansistring; is_classdef: boolean):boolean;
{ goes through all defs in st to add implementations for synthetic methods
added earlier }
procedure add_synthetic_method_implementations(st: tsymtable);
implementation
uses
verbose,systems,
tokens,scanner,
symtype,symsym,symtable,
pbase,pdecobj,psub,
defcmp;
type
tscannerstate = record
@ -65,7 +39,44 @@ implementation
valid: boolean;
end;
procedure save_scanner(out sstate: tscannerstate);
{ save/restore the scanner state before/after injecting }
procedure replace_scanner(const tempname: string; out sstate: tscannerstate);
procedure restore_scanner(const sstate: tscannerstate);
{ parses a (class or regular) method/constructor/destructor declaration from
str, as if it were declared in astruct's declaration body
WARNING: save the scanner state before calling this routine, and restore
when done. }
function str_parse_method_dec(str: ansistring; is_classdef: boolean; astruct: tabstractrecorddef; out pd: tprocdef): boolean;
{ parses a (class or regular) method/constructor/destructor implementation
from str, as if it appeared in the current unit's implementation section
WARNING: save the scanner state before calling this routine, and restore
when done. }
function str_parse_method_impl(str: ansistring; is_classdef: boolean):boolean;
{ in the JVM, constructors are not automatically inherited (so you can hide
them). To emulate the Pascal behaviour, we have to automatically add
all parent constructors to the current class as well.}
procedure add_missing_parent_constructors_intf(obj: tobjectdef);
// procedure add_missing_parent_constructors_impl(obj: tobjectdef);
{ goes through all defs in st to add implementations for synthetic methods
added earlier }
procedure add_synthetic_method_implementations(st: tsymtable);
implementation
uses
verbose,systems,
symtype,symsym,symtable,defutil,
pbase,pdecobj,psub,
defcmp;
procedure replace_scanner(const tempname: string; out sstate: tscannerstate);
begin
{ would require saving of idtoken, pattern etc }
if (token=_ID) then
@ -74,6 +85,7 @@ implementation
sstate.old_token:=token;
sstate.old_c:=c;
sstate.valid:=true;
current_scanner:=tscannerfile.Create('_Macro_.'+tempname);
end;
@ -93,6 +105,7 @@ implementation
var
oldparse_only: boolean;
begin
Message1(parser_d_internal_parser_string,str);
oldparse_only:=parse_only;
parse_only:=true;
result:=false;
@ -115,6 +128,7 @@ implementation
var
oldparse_only: boolean;
begin
Message1(parser_d_internal_parser_string,str);
oldparse_only:=parse_only;
parse_only:=false;
result:=false;
@ -174,10 +188,7 @@ implementation
{ if we get here, we did not find it in the current objectdef ->
add }
if not sstate.valid then
begin
save_scanner(sstate);
current_scanner:=tscannerfile.Create('_Macro_.parent_constructors_intf');
end;
replace_scanner('parent_constructors_intf',sstate);
isclassmethod:=
(po_classmethod in tprocdef(pd).procoptions) and
not(tprocdef(pd).proctypeoption in [potype_constructor,potype_destructor]);
@ -231,10 +242,7 @@ implementation
not(oo_is_external in tobjectdef(def).objectoptions) then
begin
if not sstate.valid then
begin
save_scanner(sstate);
current_scanner:=tscannerfile.Create('_Macro_.parent_constructors_impl');
end;
replace_scanner('synthetic_impl',sstate);
add_missing_parent_constructors_impl(tobjectdef(def));
end;
end;