Hi,
and why is it not inlining the count and append call of this string
builder? It is not using any implementation only function
unit inlinetest;
{$mode objfpc}{$H+}
interface
uses
Classes, SysUtils,math;
type TStrBuilder = object
protected
next, bufferend: pchar; //next empty pchar and first pos after the string
public
buffer: pstring;
procedure init(abuffer:pstring);
procedure final;
function count: SizeInt; inline;
procedure reserveadd(delta: SizeInt);
procedure append(c: char); inline;
procedure append(const s: RawByteString); inline;
procedure append(const p: pchar; const l: SizeInt); inline;
end;
implementation
procedure TStrBuilder.init(abuffer: pstring);
begin
buffer := abuffer;
SetLength(buffer^, 16); //use setlength to create a new string
next := pchar(buffer^);
bufferend := next + length(buffer^);
end;
procedure TStrBuilder.final;
begin
if next <> bufferend then begin
setlength(buffer^, count); // !!! Note: Call to subroutine
"function TStrBuilder.count:Int64;" marked as inline is not inlined
next := pchar(buffer^) + length(buffer^);
bufferend := next;
end;
end;
function TStrBuilder.count: SizeInt;
begin
result := next - pointer(buffer^);
end;
procedure TStrBuilder.reserveadd(delta: SizeInt);
var
oldlen: SizeInt;
begin
if next + delta > bufferend then begin
oldlen := count;
SetLength(buffer^, max(2*length(buffer^), oldlen + delta));
next := pchar(buffer^) + oldlen;
bufferend := pchar(buffer^) + length(buffer^);
end;
end;
procedure TStrBuilder.append(c: char);
begin
if next >= bufferend then reserveadd(1);
next^ := c;
inc(next);
end;
procedure TStrBuilder.append(const s: RawByteString);
begin
append(pchar(pointer(s)), length(s)); // !!! inlinetest.pas(71,3)
Note: Call to subroutine "procedure TStrBuilder.append(const
p:PChar;const l:Int64);" marked as inline is not inlined
end;
procedure TStrBuilder.append(const p: pchar; const l: SizeInt); inline;
begin
if l <= 0 then exit;
if next + l > bufferend then reserveadd(l);
move(p^, next^, l);
inc(next, l);
end;
end.
Bye,
Benito
Am 29.12.18 um 20:31 schrieb Sven Barth via fpc-pascal:
Am Sa., 29. Dez. 2018, 15:23 hat Benito van der Zander
<ben...@benibela.de <mailto:ben...@benibela.de>> geschrieben:
Hi,
after updating from fpc 3.1 to fpc 3.3, I am getting a lot of
"function
was not inlined" warnings, e.g. when an inline function depends on a
function not declared in the interface part like:
unit inlinetest;
{$mode objfpc}{$H+}
interface
uses
Classes, SysUtils;
function strContains(const str, searched: string): boolean; inline;
implementation
function strContainsFrom(const str, searched: string; from: SizeInt):
boolean;
begin
result:=Pos(searched, str, from) > 0;
end;
function strContains(const str, searched: string): boolean; inline;
begin
result := strContainsFrom(str, searched, 1);
end;
end.
Is that supposed to happen?
Fpc 3.1 did not show any warning in this case (although now that I
investigate it, fpc 3.1 also did not seem to inline it despite not
showing the warning)
Correct. FPC 3.1.1 did neither warn nor inline in this case, 3.3.1 at
least warns (I think 3.2 already warns as well).
Regards,
Sven
_______________________________________________
fpc-pascal maillist - fpc-pascal@lists.freepascal.org
http://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-pascal
_______________________________________________
fpc-pascal maillist - fpc-pascal@lists.freepascal.org
http://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-pascal