mirror of
https://gitlab.com/freepascal.org/fpc/source.git
synced 2025-04-23 23:09:38 +02:00
* use separate pools for obj-c strings and string references
git-svn-id: branches/objc@13670 -
This commit is contained in:
parent
d56a936520
commit
ab8e119c3e
1
.gitattributes
vendored
1
.gitattributes
vendored
@ -8224,6 +8224,7 @@ tests/test/tobjc13.pp svneol=native#text/plain
|
||||
tests/test/tobjc14.pp svneol=native#text/plain
|
||||
tests/test/tobjc15.pp svneol=native#text/plain
|
||||
tests/test/tobjc16.pp svneol=native#text/plain
|
||||
tests/test/tobjc17.pp svneol=native#text/plain
|
||||
tests/test/tobjc2.pp svneol=native#text/plain
|
||||
tests/test/tobjc3.pp svneol=native#text/plain
|
||||
tests/test/tobjc4.pp svneol=native#text/plain
|
||||
|
@ -82,10 +82,11 @@ interface
|
||||
sp_ansistr,
|
||||
sp_widestr,
|
||||
sp_unicodestr,
|
||||
sp_objcmetaclass,
|
||||
sp_objcclassnamerefs,
|
||||
sp_varnamerefs,
|
||||
sp_objcclassnames,
|
||||
sp_objcvarnames,
|
||||
sp_objcvartypes,
|
||||
sp_objcclassnames
|
||||
sp_objcvartypes
|
||||
);
|
||||
|
||||
const
|
||||
|
@ -115,12 +115,12 @@ implementation
|
||||
else
|
||||
begin
|
||||
{ find/add necessary classref/classname pool entries }
|
||||
if current_asmdata.ConstPools[sp_objcmetaclass]=nil then
|
||||
current_asmdata.ConstPools[sp_objcmetaclass]:=THashSet.Create(64, True, False);
|
||||
pool:=current_asmdata.ConstPools[sp_objcmetaclass];
|
||||
if current_asmdata.ConstPools[sp_objcclassnamerefs]=nil then
|
||||
current_asmdata.ConstPools[sp_objcclassnamerefs]:=THashSet.Create(64, True, False);
|
||||
pool:=current_asmdata.ConstPools[sp_objcclassnamerefs];
|
||||
typename:=left.resultdef.gettypename;
|
||||
entry:=pool.FindOrAdd(@typename[1],length(typename));
|
||||
objcfinishstringrefpoolentry(entry,sec_objc_cls_refs,sec_objc_class_names);
|
||||
objcfinishstringrefpoolentry(entry,sp_objcclassnames,sec_objc_cls_refs,sec_objc_class_names);
|
||||
reference_reset_symbol(href,tasmlabel(entry^.Data),0,sizeof(pint));
|
||||
cg.a_load_ref_reg(current_asmdata.CurrAsmList,OS_ADDR,OS_ADDR,href,location.register);
|
||||
end;
|
||||
|
@ -61,9 +61,9 @@ procedure tcgobjcselectornode.pass_generate_code;
|
||||
name : pshortstring;
|
||||
pc : pchar;
|
||||
begin
|
||||
if current_asmdata.ConstPools[sp_objcvarnames]=nil then
|
||||
current_asmdata.ConstPools[sp_objcvarnames]:=THashSet.Create(64, True, False);
|
||||
pool:=current_asmdata.ConstPools[sp_objcvarnames];
|
||||
if current_asmdata.ConstPools[sp_varnamerefs]=nil then
|
||||
current_asmdata.ConstPools[sp_varnamerefs]:=THashSet.Create(64, True, False);
|
||||
pool:=current_asmdata.ConstPools[sp_varnamerefs];
|
||||
|
||||
case left.nodetype of
|
||||
loadn:
|
||||
@ -83,7 +83,7 @@ procedure tcgobjcselectornode.pass_generate_code;
|
||||
internalerror(2009030701);
|
||||
end;
|
||||
|
||||
objcfinishstringrefpoolentry(entry,sec_objc_message_refs,sec_objc_meth_var_names);
|
||||
objcfinishstringrefpoolentry(entry,sp_objcvarnames,sec_objc_message_refs,sec_objc_meth_var_names);
|
||||
|
||||
location_reset_ref(location,LOC_CREFERENCE,def_cgsize(resultdef),sizeof(pint));
|
||||
location.reference.symbol:=tasmlabel(entry^.Data);
|
||||
|
@ -29,10 +29,10 @@ interface
|
||||
|
||||
uses
|
||||
cclasses,
|
||||
aasmbase,
|
||||
aasmbase,aasmdata,
|
||||
symbase;
|
||||
|
||||
procedure objcfinishstringrefpoolentry(entry: phashsetitem; refsec, stringsec: tasmsectiontype);
|
||||
procedure objcfinishstringrefpoolentry(entry: phashsetitem; stringpool: tconstpooltype; refsec, stringsec: tasmsectiontype);
|
||||
|
||||
procedure MaybeGenerateObjectiveCImageInfo(globalst, localst: tsymtable);
|
||||
|
||||
@ -42,7 +42,7 @@ implementation
|
||||
uses
|
||||
globtype,globals,
|
||||
systems,
|
||||
aasmdata,aasmtai,
|
||||
aasmtai,
|
||||
cgbase,cgutils,
|
||||
objcutil,
|
||||
symconst,symtype,symsym,symdef,symtable,
|
||||
@ -53,38 +53,7 @@ implementation
|
||||
String section helpers
|
||||
*******************************************************************}
|
||||
|
||||
procedure objcfinishstringrefpoolentry(entry: phashsetitem; refsec, stringsec: tasmsectiontype);
|
||||
var
|
||||
reflab,
|
||||
strlab : tasmlabel;
|
||||
pc : pchar;
|
||||
begin
|
||||
{ have we already generated this selector? }
|
||||
if not assigned(entry^.Data) then
|
||||
begin
|
||||
{ create new one
|
||||
(no getdatalabel, because these labels have to be local)
|
||||
}
|
||||
current_asmdata.getlabel(reflab,alt_data);
|
||||
current_asmdata.getlabel(strlab,alt_data);
|
||||
entry^.Data:=reflab;
|
||||
getmem(pc,entry^.keylength+1);
|
||||
move(entry^.key^,pc^,entry^.keylength);
|
||||
pc[entry^.keylength]:=#0;
|
||||
{ add a pointer to the message name in the string references section }
|
||||
new_section(current_asmdata.asmlists[al_objc_pools],refsec,reflab.name,sizeof(pint));
|
||||
current_asmdata.asmlists[al_objc_pools].concat(Tai_label.Create(reflab));
|
||||
current_asmdata.asmlists[al_objc_pools].concat(Tai_const.Create_sym(strlab));
|
||||
|
||||
{ and now add the message name to the associated strings section }
|
||||
new_section(current_asmdata.asmlists[al_objc_pools],stringsec,strlab.name,sizeof(pint));
|
||||
current_asmdata.asmlists[al_objc_pools].concat(Tai_label.Create(strlab));
|
||||
current_asmdata.asmlists[al_objc_pools].concat(Tai_string.Create_pchar(pc,entry^.keylength+1));
|
||||
end;
|
||||
end;
|
||||
|
||||
|
||||
function objcreatestringpoolentry(const s: string; pooltype: tconstpooltype; stringsec: tasmsectiontype): TAsmSymbol;
|
||||
function objcreatestringpoolentryintern(p: pchar; len: longint; pooltype: tconstpooltype; stringsec: tasmsectiontype): TAsmSymbol;
|
||||
var
|
||||
entry : PHashSetItem;
|
||||
strlab : tasmlabel;
|
||||
@ -95,7 +64,7 @@ function objcreatestringpoolentry(const s: string; pooltype: tconstpooltype; str
|
||||
current_asmdata.ConstPools[pooltype]:=THashSet.Create(64, True, False);
|
||||
pool := current_asmdata.constpools[pooltype];
|
||||
|
||||
entry:=pool.FindOrAdd(@s[1],length(s));
|
||||
entry:=pool.FindOrAdd(p,len);
|
||||
if not assigned(entry^.data) then
|
||||
begin
|
||||
{ create new entry }
|
||||
@ -116,6 +85,39 @@ function objcreatestringpoolentry(const s: string; pooltype: tconstpooltype; str
|
||||
end;
|
||||
|
||||
|
||||
procedure objcfinishstringrefpoolentry(entry: phashsetitem; stringpool: tconstpooltype; refsec, stringsec: tasmsectiontype);
|
||||
var
|
||||
reflab : tasmlabel;
|
||||
strlab : tasmsymbol;
|
||||
pc : pchar;
|
||||
begin
|
||||
{ have we already generated a reference for this string entry? }
|
||||
if not assigned(entry^.Data) then
|
||||
begin
|
||||
{ no, add the string to the associated strings section }
|
||||
strlab:=objcreatestringpoolentryintern(pchar(entry^.key),entry^.keylength,stringpool,stringsec);
|
||||
|
||||
{ and now finish the reference }
|
||||
current_asmdata.getlabel(reflab,alt_data);
|
||||
entry^.Data:=reflab;
|
||||
getmem(pc,entry^.keylength+1);
|
||||
move(entry^.key^,pc^,entry^.keylength);
|
||||
pc[entry^.keylength]:=#0;
|
||||
{ add a pointer to the message name in the string references section }
|
||||
new_section(current_asmdata.asmlists[al_objc_pools],refsec,reflab.name,sizeof(pint));
|
||||
current_asmdata.asmlists[al_objc_pools].concat(Tai_label.Create(reflab));
|
||||
current_asmdata.asmlists[al_objc_pools].concat(Tai_const.Create_sym(strlab));
|
||||
end;
|
||||
end;
|
||||
|
||||
|
||||
|
||||
function objcreatestringpoolentry(const s: string; pooltype: tconstpooltype; stringsec: tasmsectiontype): TAsmSymbol;
|
||||
begin
|
||||
result:=objcreatestringpoolentryintern(@s[1],length(s),pooltype,stringsec);
|
||||
end;
|
||||
|
||||
|
||||
{******************************************************************
|
||||
RTTI generation
|
||||
*******************************************************************}
|
||||
|
30
tests/test/tobjc17.pp
Normal file
30
tests/test/tobjc17.pp
Normal file
@ -0,0 +1,30 @@
|
||||
{ %target=darwin }
|
||||
{ %cpu=powerpc,i386 }
|
||||
|
||||
program project1;
|
||||
|
||||
{$mode objfpc}{$H+}
|
||||
{$modeswitch objectivec1}
|
||||
type
|
||||
MyObject = objcclass(NSObject)
|
||||
private
|
||||
data : Integer;
|
||||
public
|
||||
procedure setData_(aData: Integer); message 'setData:';
|
||||
end;
|
||||
|
||||
procedure MyObject.setData_(aData: Integer);
|
||||
begin
|
||||
data := aData;
|
||||
end;
|
||||
|
||||
var
|
||||
m : MyObject;
|
||||
|
||||
begin
|
||||
m := MyObject.alloc;
|
||||
m.setData_(5);
|
||||
if (m.data<>5) then
|
||||
halt(1);
|
||||
m.release;
|
||||
end.
|
Loading…
Reference in New Issue
Block a user