mirror of
https://gitlab.com/freepascal.org/fpc/source.git
synced 2025-09-11 20:29:14 +02:00
+ user section type
+ parsing of section directive for variables + section test + write section names in the assembler/binary writers correctly * allow section only after ; and for embedded targets git-svn-id: branches/usersections@17154 -
This commit is contained in:
parent
e4656050a7
commit
f328b6d635
1
.gitattributes
vendored
1
.gitattributes
vendored
@ -9972,6 +9972,7 @@ tests/test/tsealed3.pp svneol=native#text/pascal
|
||||
tests/test/tsealed4.pp svneol=native#text/pascal
|
||||
tests/test/tsealed5.pp svneol=native#text/pascal
|
||||
tests/test/tsealed6.pp svneol=native#text/pascal
|
||||
tests/test/tsec1.pp svneol=native#text/plain
|
||||
tests/test/tsel1.pp svneol=native#text/plain
|
||||
tests/test/tsel2.pp svneol=native#text/plain
|
||||
tests/test/tset1.pp svneol=native#text/plain
|
||||
|
@ -61,6 +61,8 @@ interface
|
||||
|
||||
type
|
||||
TAsmSectiontype=(sec_none,
|
||||
{ this section type allows to define a user named section }
|
||||
sec_user,
|
||||
sec_code,
|
||||
sec_data,
|
||||
{ read-only, but may contain relocations }
|
||||
|
@ -246,7 +246,7 @@ implementation
|
||||
|
||||
function TGNUAssembler.sectionname(atype:TAsmSectiontype;const aname:string;aorder:TAsmSectionOrder):string;
|
||||
const
|
||||
secnames : array[TAsmSectiontype] of string[length('__DATA, __datacoal_nt,coalesced')] = ('',
|
||||
secnames : array[TAsmSectiontype] of string[length('__DATA, __datacoal_nt,coalesced')] = ('','',
|
||||
'.text',
|
||||
'.data',
|
||||
{ why doesn't .rodata work? (FK) }
|
||||
@ -264,7 +264,7 @@ implementation
|
||||
{$if defined(m68k)} { Amiga/m68k GNU AS doesn't seem to like .rodata (KB) }
|
||||
'.data',
|
||||
{$else}
|
||||
'.rodata',
|
||||
'.rodata',
|
||||
{$endif}
|
||||
'.bss',
|
||||
'.threadvar',
|
||||
@ -318,7 +318,7 @@ implementation
|
||||
'.obcj_nlcatlist',
|
||||
'.objc_protolist'
|
||||
);
|
||||
secnames_pic : array[TAsmSectiontype] of string[length('__DATA, __datacoal_nt,coalesced')] = ('',
|
||||
secnames_pic : array[TAsmSectiontype] of string[length('__DATA, __datacoal_nt,coalesced')] = ('','',
|
||||
'.text',
|
||||
'.data.rel',
|
||||
'.data.rel',
|
||||
@ -406,6 +406,10 @@ implementation
|
||||
(target_info.system=system_i386_go32v2) then
|
||||
secname:='.data';
|
||||
|
||||
{ section type user gives the user full controll on the section name }
|
||||
if atype=sec_user then
|
||||
secname:=aname;
|
||||
|
||||
{ For bss we need to set some flags that are target dependent,
|
||||
it is easier to disable it for smartlinking. It doesn't take up
|
||||
filespace }
|
||||
@ -413,6 +417,7 @@ implementation
|
||||
create_smartlink_sections and
|
||||
(aname<>'') and
|
||||
(atype<>sec_toc) and
|
||||
(atype<>sec_user) and
|
||||
{ on embedded systems every byte counts, so smartlink bss too }
|
||||
((atype<>sec_bss) or (target_info.system in systems_embedded)) then
|
||||
begin
|
||||
@ -1466,6 +1471,7 @@ implementation
|
||||
const
|
||||
(* Translation table - replace unsupported section types with basic ones. *)
|
||||
SecXTable: array[TAsmSectionType] of TAsmSectionType = (
|
||||
sec_none,
|
||||
sec_none,
|
||||
sec_code,
|
||||
sec_data,
|
||||
|
@ -445,7 +445,7 @@ interface
|
||||
|
||||
procedure T386NasmAssembler.WriteSection(atype:TAsmSectiontype;const aname:string);
|
||||
const
|
||||
secnames : array[TAsmSectiontype] of string[length('__DATA, __datacoal_nt,coalesced')] = ('',
|
||||
secnames : array[TAsmSectiontype] of string[length('__DATA, __datacoal_nt,coalesced')] = ('','',
|
||||
'.text',
|
||||
'.data',
|
||||
'.data',
|
||||
|
@ -1366,6 +1366,10 @@ parser_e_cant_use_type_parameters_here=03304_E_Type parameters may require initi
|
||||
% Type parameters may be specialized with types which (e.g. \var{ansistring}) need initialization/finalization
|
||||
% code which is implicitly generated by the compiler.
|
||||
% \end{description}
|
||||
parser_e_externals_no_section=03305_E_Variables being declared as external cannot be in a custom section
|
||||
% A section directive is not valid for variables being declared as external.
|
||||
parser_e_section_no_locals=03306_E_Non-static and non-global variables cannot have a section directive
|
||||
% A variable placed in a custom section is always statically allocated so it must be either a static or global variable.
|
||||
# Type Checking
|
||||
#
|
||||
# 04095 is the last used one
|
||||
|
@ -393,6 +393,8 @@ const
|
||||
parser_e_no_constructor_in_records=03302;
|
||||
parser_e_at_least_one_argument_must_be_of_type=03303;
|
||||
parser_e_cant_use_type_parameters_here=03304;
|
||||
parser_e_externals_no_section=03305;
|
||||
parser_e_section_no_locals=03306;
|
||||
type_e_mismatch=04000;
|
||||
type_e_incompatible_types=04001;
|
||||
type_e_not_equal_types=04002;
|
||||
@ -882,9 +884,9 @@ const
|
||||
option_info=11024;
|
||||
option_help_pages=11025;
|
||||
|
||||
MsgTxtSize = 58686;
|
||||
MsgTxtSize = 58837;
|
||||
|
||||
MsgIdxMax : array[1..20] of longint=(
|
||||
24,88,305,99,84,54,111,22,202,63,
|
||||
24,88,307,99,84,54,111,22,202,63,
|
||||
49,20,1,1,1,1,1,1,1,1
|
||||
);
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -2524,7 +2524,10 @@ implementation
|
||||
sectype:=sec_bss;
|
||||
end;
|
||||
maybe_new_object_file(list);
|
||||
new_section(list,sectype,lower(sym.mangledname),varalign);
|
||||
if sym.section<>'' then
|
||||
new_section(list,sec_user,sym.section,varalign)
|
||||
else
|
||||
new_section(list,sectype,lower(sym.mangledname),varalign);
|
||||
if (sym.owner.symtabletype=globalsymtable) or
|
||||
create_smartlink or
|
||||
DLLSource or
|
||||
|
@ -823,7 +823,7 @@ implementation
|
||||
|
||||
function TObjData.sectionname(atype:TAsmSectiontype;const aname:string;aorder:TAsmSectionOrder):string;
|
||||
const
|
||||
secnames : array[TAsmSectiontype] of string[length('__DATA, __datacoal_nt,coalesced')] = ('',
|
||||
secnames : array[TAsmSectiontype] of string[length('__DATA, __datacoal_nt,coalesced')] = ('','',
|
||||
'code',
|
||||
'Data',
|
||||
'Data',
|
||||
@ -902,6 +902,7 @@ implementation
|
||||
function TObjData.sectiontype2options(atype:TAsmSectiontype):TObjSectionOptions;
|
||||
const
|
||||
secoptions : array[TAsmSectiontype] of TObjSectionOptions = ([],
|
||||
{user} [oso_Data,oso_load,oso_write,oso_executable,oso_keep],
|
||||
{code} [oso_Data,oso_load,oso_readonly,oso_executable,oso_keep],
|
||||
{Data} [oso_Data,oso_load,oso_write,oso_keep],
|
||||
{ TODO: Fix sec_rodata be read-only-with-relocs}
|
||||
|
@ -488,7 +488,7 @@ implementation
|
||||
SymbolMaxGrow = 200*sizeof(coffsymbol);
|
||||
StrsMaxGrow = 8192;
|
||||
|
||||
coffsecnames : array[TAsmSectiontype] of string[length('__DATA, __datacoal_nt,coalesced')] = ('',
|
||||
coffsecnames : array[TAsmSectiontype] of string[length('__DATA, __datacoal_nt,coalesced')] = ('','',
|
||||
'.text','.data','.data','.data','.bss','.tls',
|
||||
'.pdata',{pdata}
|
||||
'.text', {stub}
|
||||
@ -1031,22 +1031,28 @@ const pemagic : array[0..3] of byte = (
|
||||
sep : string[3];
|
||||
secname : string;
|
||||
begin
|
||||
secname:=coffsecnames[atype];
|
||||
if create_smartlink_sections and
|
||||
(aname<>'') then
|
||||
begin
|
||||
case aorder of
|
||||
secorder_begin :
|
||||
sep:='.b_';
|
||||
secorder_end :
|
||||
sep:='.z_';
|
||||
else
|
||||
sep:='.n_';
|
||||
end;
|
||||
result:=secname+sep+aname
|
||||
end
|
||||
{ section type user gives the user full controll on the section name }
|
||||
if atype=sec_user then
|
||||
result:=aname
|
||||
else
|
||||
result:=secname;
|
||||
begin
|
||||
secname:=coffsecnames[atype];
|
||||
if create_smartlink_sections and
|
||||
(aname<>'') then
|
||||
begin
|
||||
case aorder of
|
||||
secorder_begin :
|
||||
sep:='.b_';
|
||||
secorder_end :
|
||||
sep:='.z_';
|
||||
else
|
||||
sep:='.n_';
|
||||
end;
|
||||
result:=secname+sep+aname
|
||||
end
|
||||
else
|
||||
result:=secname;
|
||||
end;
|
||||
end;
|
||||
|
||||
|
||||
|
@ -584,7 +584,7 @@ implementation
|
||||
|
||||
function TElfObjData.sectionname(atype:TAsmSectiontype;const aname:string;aorder:TAsmSectionOrder):string;
|
||||
const
|
||||
secnames : array[TAsmSectiontype] of string[length('__DATA, __datacoal_nt,coalesced')] = ('',
|
||||
secnames : array[TAsmSectiontype] of string[length('__DATA, __datacoal_nt,coalesced')] = ('','',
|
||||
{$ifdef userodata}
|
||||
'.text','.data','.data','.rodata','.bss','.threadvar',
|
||||
{$else userodata}
|
||||
@ -639,7 +639,7 @@ implementation
|
||||
'.obcj_nlcatlist',
|
||||
'.objc_protolist'
|
||||
);
|
||||
secnames_pic : array[TAsmSectiontype] of string[length('__DATA, __datacoal_nt,coalesced')] = ('',
|
||||
secnames_pic : array[TAsmSectiontype] of string[length('__DATA, __datacoal_nt,coalesced')] = ('','',
|
||||
'.text',
|
||||
'.data.rel',
|
||||
'.data.rel',
|
||||
@ -700,30 +700,36 @@ implementation
|
||||
sep : string[3];
|
||||
secname : string;
|
||||
begin
|
||||
if (cs_create_pic in current_settings.moduleswitches) and
|
||||
not(target_info.system in systems_darwin) then
|
||||
secname:=secnames_pic[atype]
|
||||
{ section type user gives the user full controll on the section name }
|
||||
if atype=sec_user then
|
||||
result:=aname
|
||||
else
|
||||
secname:=secnames[atype];
|
||||
if (atype=sec_fpc) and (Copy(aname,1,3)='res') then
|
||||
begin
|
||||
result:=secname+'.'+aname;
|
||||
exit;
|
||||
if (cs_create_pic in current_settings.moduleswitches) and
|
||||
not(target_info.system in systems_darwin) then
|
||||
secname:=secnames_pic[atype]
|
||||
else
|
||||
secname:=secnames[atype];
|
||||
if (atype=sec_fpc) and (Copy(aname,1,3)='res') then
|
||||
begin
|
||||
result:=secname+'.'+aname;
|
||||
exit;
|
||||
end;
|
||||
if create_smartlink_sections and (aname<>'') then
|
||||
begin
|
||||
case aorder of
|
||||
secorder_begin :
|
||||
sep:='.b_';
|
||||
secorder_end :
|
||||
sep:='.z_';
|
||||
else
|
||||
sep:='.n_';
|
||||
end;
|
||||
result:=secname+sep+aname
|
||||
end
|
||||
else
|
||||
result:=secname;
|
||||
end;
|
||||
if create_smartlink_sections and (aname<>'') then
|
||||
begin
|
||||
case aorder of
|
||||
secorder_begin :
|
||||
sep:='.b_';
|
||||
secorder_end :
|
||||
sep:='.z_';
|
||||
else
|
||||
sep:='.n_';
|
||||
end;
|
||||
result:=secname+sep+aname
|
||||
end
|
||||
else
|
||||
result:=secname;
|
||||
end;
|
||||
|
||||
|
||||
|
@ -180,6 +180,7 @@ implementation
|
||||
= ('sec_debug_frame','__debug_info','__debug_line','__debug_abbrev');
|
||||
begin
|
||||
case atype of
|
||||
sec_user: Result:=aname;
|
||||
sec_bss: Result:=MakeSectionName(seg_DATA, '__common');
|
||||
sec_stab: Result:='.stabs';
|
||||
sec_stabstr: Result:='.stabsstr';
|
||||
|
@ -1041,6 +1041,17 @@ implementation
|
||||
end;
|
||||
|
||||
|
||||
procedure try_consume_sectiondirective(var asection: ansistring);
|
||||
begin
|
||||
if idtoken=_SECTION then
|
||||
begin
|
||||
consume(_ID);
|
||||
asection:=get_stringconst;
|
||||
consume(_SEMICOLON);
|
||||
end;
|
||||
end;
|
||||
|
||||
|
||||
procedure read_var_decls(options:Tvar_dec_options);
|
||||
|
||||
procedure read_default_value(sc : TFPObjectList);
|
||||
@ -1253,6 +1264,7 @@ implementation
|
||||
hintsymoptions : tsymoptions;
|
||||
deprecatedmsg : pshortstring;
|
||||
old_block_type : tblock_type;
|
||||
section : ansistring;
|
||||
begin
|
||||
old_block_type:=block_type;
|
||||
block_type:=bt_var;
|
||||
@ -1394,6 +1406,24 @@ implementation
|
||||
) then
|
||||
read_public_and_external_sc(sc);
|
||||
|
||||
{ try to parse a section directive }
|
||||
if (target_info.system in systems_embedded) and (idtoken=_SECTION) then
|
||||
begin
|
||||
try_consume_sectiondirective(section);
|
||||
if section<>'' then
|
||||
begin
|
||||
for i:=0 to sc.count-1 do
|
||||
begin
|
||||
vs:=tabstractvarsym(sc[i]);
|
||||
if (vs.varoptions *[vo_is_external,vo_is_weak_external])<>[] then
|
||||
Message(parser_e_externals_no_section);
|
||||
if vs.typ<>staticvarsym then
|
||||
Message(parser_e_section_no_locals);
|
||||
tstaticvarsym(vs).section:=section;
|
||||
end;
|
||||
end;
|
||||
end;
|
||||
|
||||
{ allocate normal variable (non-external and non-typed-const) staticvarsyms }
|
||||
for i:=0 to sc.count-1 do
|
||||
begin
|
||||
|
@ -70,6 +70,7 @@ interface
|
||||
|
||||
secnames : array[TAsmSectiontype] of string[10] = (
|
||||
'', {none}
|
||||
'', {user}
|
||||
'csect', {code}
|
||||
'csect', {data}
|
||||
'csect', {read only data}
|
||||
|
@ -423,7 +423,8 @@ type
|
||||
vo_is_msgsel,
|
||||
{ first field of variant part of a record }
|
||||
vo_is_first_field,
|
||||
vo_volatile
|
||||
vo_volatile,
|
||||
vo_has_section
|
||||
);
|
||||
tvaroptions=set of tvaroption;
|
||||
|
||||
|
@ -200,6 +200,7 @@ interface
|
||||
private
|
||||
_mangledname : pshortstring;
|
||||
public
|
||||
section : ansistring;
|
||||
constructor create(const n : string;vsp:tvarspez;def:tdef;vopts:tvaroptions);
|
||||
constructor create_dll(const n : string;vsp:tvarspez;def:tdef);
|
||||
constructor create_C(const n,mangled : string;vsp:tvarspez;def:tdef);
|
||||
@ -1312,6 +1313,8 @@ implementation
|
||||
_mangledname:=stringdup(ppufile.getstring)
|
||||
else
|
||||
_mangledname:=nil;
|
||||
if vo_has_section in varoptions then
|
||||
section:=ppufile.getansistring;
|
||||
end;
|
||||
|
||||
|
||||
@ -1336,6 +1339,8 @@ implementation
|
||||
inherited ppuwrite(ppufile);
|
||||
if vo_has_mangledname in varoptions then
|
||||
ppufile.putstring(_mangledname^);
|
||||
if vo_has_section in varoptions then
|
||||
ppufile.putansistring(section);
|
||||
ppufile.writeentry(ibstaticvarsym);
|
||||
end;
|
||||
|
||||
|
@ -204,6 +204,7 @@ type
|
||||
_PROGRAM,
|
||||
_R12BASE,
|
||||
_STDCALL,
|
||||
_SECTION,
|
||||
_SYSCALL,
|
||||
_VARARGS,
|
||||
_VIRTUAL,
|
||||
@ -498,6 +499,7 @@ const
|
||||
(str:'PROGRAM' ;special:false;keyword:m_all;op:NOTOKEN),
|
||||
(str:'R12BASE' ;special:false;keyword:m_none;op:NOTOKEN), { Syscall variation on MorphOS }
|
||||
(str:'STDCALL' ;special:false;keyword:m_none;op:NOTOKEN),
|
||||
(str:'SECTION' ;special:false;keyword:m_none;op:NOTOKEN),
|
||||
(str:'SYSCALL' ;special:false;keyword:m_none;op:NOTOKEN),
|
||||
(str:'VARARGS' ;special:false;keyword:m_none;op:NOTOKEN),
|
||||
(str:'VIRTUAL' ;special:false;keyword:m_none;op:NOTOKEN),
|
||||
|
@ -59,7 +59,7 @@ implementation
|
||||
const
|
||||
line_length = 70;
|
||||
|
||||
secnames : array[TAsmSectiontype] of string[4] = ('',
|
||||
secnames : array[TAsmSectiontype] of string[4] = ('','',
|
||||
'CODE','DATA','DATA','DATA','BSS','',
|
||||
'','','','','','',
|
||||
'','','','',
|
||||
@ -109,7 +109,7 @@ implementation
|
||||
''
|
||||
);
|
||||
|
||||
secnamesml64 : array[TAsmSectiontype] of string[7] = ('',
|
||||
secnamesml64 : array[TAsmSectiontype] of string[7] = ('','',
|
||||
'_TEXT','_DATE','_DATA','_DATA','_BSS','',
|
||||
'','','','',
|
||||
'idata$2','idata$4','idata$5','idata$6','idata$7','edata',
|
||||
@ -978,7 +978,7 @@ implementation
|
||||
|
||||
{ better do this at end of WriteTree, but then there comes a trouble with
|
||||
al_const which does not have leading ait_section and thus goes out of segment }
|
||||
|
||||
|
||||
{ TODO: probably ml64 needs 'closing' last section, too }
|
||||
if LastSecType <> sec_none then
|
||||
AsmWriteLn('_'+secnames[LasTSecType]+#9#9'ENDS');
|
||||
|
6
tests/test/tsec1.pp
Normal file
6
tests/test/tsec1.pp
Normal file
@ -0,0 +1,6 @@
|
||||
{ %target=embedded }
|
||||
var
|
||||
d : longint;section '.bss';
|
||||
|
||||
begin
|
||||
end.
|
Loading…
Reference in New Issue
Block a user