diff --git a/compiler/symconst.pas b/compiler/symconst.pas index e56ba0e3c9..cb4125ef74 100644 --- a/compiler/symconst.pas +++ b/compiler/symconst.pas @@ -555,7 +555,8 @@ type ado_IsConstructor, // array constructor (e.g. something = [1,2,3]) ado_IsArrayOfConst, // array of const ado_IsConstString, // string constant - ado_IsBitPacked // bitpacked array + ado_IsBitPacked, // bitpacked array + ado_IsVector // Vector ); tarraydefoptions=set of tarraydefoption; diff --git a/compiler/symdef.pas b/compiler/symdef.pas index 3cb9e79185..766468ab9e 100644 --- a/compiler/symdef.pas +++ b/compiler/symdef.pas @@ -558,19 +558,23 @@ interface _elementdef : tdef; _elementdefderef : tderef; procedure setelementdef(def:tdef); + class function getreusable_intern(def: tdef; elems: asizeint; const options: tarraydefoptions): tarraydef; public function elesize : asizeint; function elepackedbitsize : asizeint; function elecount : asizeuint; - constructor create_from_pointer(def:tpointerdef);virtual; - constructor create(l,h:asizeint;def:tdef);virtual; + constructor create_from_pointer(def: tpointerdef);virtual; + constructor create(l, h: asizeint; def: tdef);virtual; + constructor create_vector(l,h:asizeint; def:tdef); constructor create_openarray;virtual; - class function getreusable(def: tdef; elems: asizeint): tarraydef; virtual; + class function getreusable(def: tdef; elems: asizeint): tarraydef; + class function getreusable_vector(def: tdef; elems: asizeint): tarraydef; { same as above, but in case the def must never be freed after the current module has been compiled -- even if the def was not written to the ppu file (for defs in para locations, as we don't reset them so we don't have to recalculate them all the time) } class function getreusable_no_free(def: tdef; elems: asizeint): tarraydef; + class function getreusable_no_free_vector(def: tdef; elems: asizeint): tarraydef; constructor ppuload(ppufile:tcompilerppufile); destructor destroy; override; function getcopy : tstoreddef;override; @@ -588,6 +592,7 @@ interface function needs_separate_initrtti : boolean;override; property elementdef : tdef read _elementdef write setelementdef; function is_publishable : boolean;override; + function is_hwvector: boolean; end; tarraydefclass = class of tarraydef; @@ -4035,7 +4040,7 @@ implementation TARRAYDEF ***************************************************************************} - constructor tarraydef.create(l,h:asizeint;def:tdef); + constructor tarraydef.create(l, h: asizeint; def: tdef); begin inherited create(arraydef,true); lowrange:=l; @@ -4048,6 +4053,12 @@ implementation symtable:=tarraysymtable.create(self); end; + constructor tarraydef.create_vector(l ,h: asizeint; def: tdef); + begin + self.create(l,h,def); + include(arrayoptions,ado_IsVector); + end; + constructor tarraydef.create_openarray; begin @@ -4055,19 +4066,21 @@ implementation end; - class function tarraydef.getreusable(def: tdef; elems: asizeint): tarraydef; + class function tarraydef.getreusable_intern(def: tdef; elems: asizeint; const options: tarraydefoptions): tarraydef; var res: PHashSetItem; oldsymtablestack: tsymtablestack; arrdesc: packed record def: tdef; elecount: asizeint; + options: tarraydefoptions end; begin if not assigned(current_module) then internalerror(2011081301); arrdesc.def:=def; arrdesc.elecount:=elems; + arrdesc.options:=options; res:=current_module.arraydefs.FindOrAdd(@arrdesc,sizeof(arrdesc)); if not assigned(res^.Data) then begin @@ -4082,6 +4095,7 @@ implementation symtablestack:=nil; result:=carraydef.create(0,elems-1,sizesinttype); result.elementdef:=def; + result.arrayoptions:=options; setup_reusable_def(def,result,res,oldsymtablestack); { res^.Data may still be nil -> don't overwrite result } exit; @@ -4090,6 +4104,18 @@ implementation end; + class function tarraydef.getreusable(def: tdef; elems: asizeint): tarraydef; + begin + result:=getreusable_intern(def,elems,[]); + end; + + + class function tarraydef.getreusable_vector(def: tdef; elems: asizeint): tarraydef; + begin + result:=getreusable_intern(def,elems,[ado_IsVector]); + end; + + class function tarraydef.getreusable_no_free(def: tdef; elems: asizeint): tarraydef; begin result:=getreusable(def,elems); @@ -4097,6 +4123,13 @@ implementation include(result.defoptions,df_not_registered_no_free); end; + class function tarraydef.getreusable_no_free_vector(def: tdef; elems: asizeint): tarraydef; + begin + result:=getreusable_vector(def,elems); + if not result.is_registered then + include(result.defoptions,df_not_registered_no_free); + end; + destructor tarraydef.destroy; begin @@ -4295,8 +4328,10 @@ implementation function tarraydef.alignment : shortint; begin + if ado_IsVector in arrayoptions then + alignment:=size { alignment of dyn. arrays doesn't depend on the element size } - if (ado_IsDynamicArray in arrayoptions) then + else if ado_IsDynamicArray in arrayoptions then alignment:=voidpointertype.alignment { alignment is the target alignment for the used load size } else if (ado_IsBitPacked in arrayoptions) and @@ -4368,6 +4403,12 @@ implementation Result:=ado_IsDynamicArray in arrayoptions; end; + + function tarraydef.is_hwvector: boolean; + begin + result:=ado_IsVector in arrayoptions; + end; + {*************************************************************************** tabstractrecorddef ***************************************************************************} diff --git a/compiler/utils/ppuutils/ppudump.pp b/compiler/utils/ppuutils/ppudump.pp index d466336e87..3a188f2885 100644 --- a/compiler/utils/ppuutils/ppudump.pp +++ b/compiler/utils/ppuutils/ppudump.pp @@ -3251,7 +3251,8 @@ const { ado_IsConstructor } 'IsConstructor', { ado_IsArrayOfConst } 'ArrayOfConst', { ado_IsConstString } 'ConstString', - { ado_IsBitPacked } 'BitPacked' + { ado_IsBitPacked } 'BitPacked', + { ado_IsVector } 'Vector' ); var symoptions: tarraydefoptions;