* null-terminate ansistrings like on native platforms (so support

can be added to typecast them to pchars)
  * fixed array-of-char to ansistring conversion in case of zero-based
    array and an embedded #0 (didn't stop at the embedded #0)

git-svn-id: branches/jvmbackend@18766 -
This commit is contained in:
Jonas Maebe 2011-08-20 08:34:05 +00:00
parent 27731e342c
commit 1ff004312b
3 changed files with 55 additions and 26 deletions

View File

@ -19,7 +19,7 @@ type
private private
fdata: TAnsiCharArray; fdata: TAnsiCharArray;
public public
constructor Create(const arr: array of ansichar);overload; constructor Create(const arr: array of ansichar; length: longint);overload;
constructor Create(const arr: array of unicodechar);overload; constructor Create(const arr: array of unicodechar);overload;
constructor Create(const u: unicodestring);overload; constructor Create(const u: unicodestring);overload;
constructor Create(const a: ansistring);overload; constructor Create(const a: ansistring);overload;

View File

@ -17,55 +17,75 @@
{ This will release some functions for special shortstring support } { This will release some functions for special shortstring support }
{ define EXTRAANSISHORT} { define EXTRAANSISHORT}
constructor AnsistringClass.Create(const arr: array of ansichar); constructor AnsistringClass.Create(const arr: array of ansichar; length: longint);
begin begin
{ make explicit copy so that changing the array afterwards doesn't change { make explicit copy so that changing the array afterwards doesn't change
the string } the string }
if high(arr)=-1 then if length=0 then
exit; begin
setlength(fdata,high(arr)+1); { terminating #0 }
JLSystem.ArrayCopy(JLObject(@arr),0,JLObject(fdata),0,high(arr)+1); setlength(fdata,1);
exit;
end;
setlength(fdata,length+1);
JLSystem.ArrayCopy(JLObject(@arr),0,JLObject(fdata),0,length);
// last char is already #0 because of setlength
end; end;
constructor AnsistringClass.Create(const arr: array of unicodechar); constructor AnsistringClass.Create(const arr: array of unicodechar);
begin begin
if high(arr)=-1 then if high(arr)=-1 then
exit; begin
{ terminating #0 }
setlength(fdata,1);
exit;
end;
fdata:=TAnsiCharArray(JLString.Create(arr).getBytes); fdata:=TAnsiCharArray(JLString.Create(arr).getBytes);
setlength(fdata,system.length(fdata)+1);
// last char is already #0 because of setlength
end; end;
constructor AnsistringClass.Create(const u: unicodestring); constructor AnsistringClass.Create(const u: unicodestring);
begin begin
if system.length(u)=0 then if system.length(u)=0 then
exit; begin
{ terminating #0 }
setlength(fdata,1);
exit;
end;
fdata:=TAnsiCharArray(JLString(u).getBytes); fdata:=TAnsiCharArray(JLString(u).getBytes);
setlength(fdata,system.length(fdata)+1);
// last char is already #0 because of setlength
end; end;
constructor AnsistringClass.Create(const a: ansistring); constructor AnsistringClass.Create(const a: ansistring);
begin begin
Create(AnsistringClass(a).fdata); Create(AnsistringClass(a).fdata,system.length(AnsistringClass(a).fdata)-1);
end; end;
constructor AnsistringClass.Create(const s: shortstring); constructor AnsistringClass.Create(const s: shortstring);
begin begin
Create(ShortstringClass(@s).fdata); Create(ShortstringClass(@s).fdata,system.length(ShortstringClass(@s).fdata));
end; end;
constructor AnsistringClass.Create(ch: ansichar); constructor AnsistringClass.Create(ch: ansichar);
begin begin
setlength(fdata,1); setlength(fdata,2);
fdata[0]:=ch; fdata[0]:=ch;
// last char is already #0 because of setlength
end; end;
constructor AnsistringClass.Create(ch: unicodechar); constructor AnsistringClass.Create(ch: unicodechar);
begin begin
fdata:=TAnsiCharArray(JLString.Create(ch).getBytes); fdata:=TAnsiCharArray(JLString.Create(ch).getBytes);
setlength(fdata,system.length(fdata)+1);
// last char is already #0 because of setlength
end; end;
@ -76,7 +96,8 @@ var
begin begin
{ used to construct constant ansistrings from Java string constants } { used to construct constant ansistrings from Java string constants }
res:=AnsistringClass.Create; res:=AnsistringClass.Create;
setlength(res.fdata,system.length(u)); { +1 for terminating #0 }
setlength(res.fdata,system.length(u)+1);
for i:=1 to system.length(u) do for i:=1 to system.length(u) do
res.fdata[i-1]:=ansichar(ord(u[i])); res.fdata[i-1]:=ansichar(ord(u[i]));
result:=ansistring(res); result:=ansistring(res);
@ -93,7 +114,7 @@ end;
function AnsistringClass.toUnicodeString: unicodestring; function AnsistringClass.toUnicodeString: unicodestring;
begin begin
result:=UnicodeString(JLString.Create(TJByteArray(fdata))); result:=UnicodeString(JLString.Create(TJByteArray(fdata),0,system.length(fdata)-1));
end; end;
@ -105,7 +126,7 @@ end;
function AnsistringClass.toString: JLString; function AnsistringClass.toString: JLString;
begin begin
result:=JLString.Create(TJByteArray(fdata)); result:=JLString.Create(TJByteArray(fdata),0,system.length(fdata)-1);
end; end;
(* (*
@ -149,7 +170,7 @@ end;
function AnsiStringClass.length: jint; function AnsiStringClass.length: jint;
begin begin
result:=system.length(fdata); result:=system.length(fdata)-1;
end; end;
{**************************************************************************** {****************************************************************************
@ -163,7 +184,8 @@ var
begin begin
thislen:=length(s1); thislen:=length(s1);
addlen:=length(s2); addlen:=length(s2);
setlength(newdata,thislen+addlen); { +1 for terminating #0 }
setlength(newdata,thislen+addlen+1);
if thislen>0 then if thislen>0 then
JLSystem.ArrayCopy(JLObject(AnsistringClass(s1).fdata),0,JLObject(newdata),0,thislen); JLSystem.ArrayCopy(JLObject(AnsistringClass(s1).fdata),0,JLObject(newdata),0,thislen);
if addlen>0 then if addlen>0 then
@ -186,7 +208,8 @@ procedure fpc_AnsiStr_Concat_multi (var DestS:Ansistring;const sarr:array of Ans
NewSize:=0; NewSize:=0;
for i:=low(sarr) to high(sarr) do for i:=low(sarr) to high(sarr) do
inc(newsize,length(sarr[i])); inc(newsize,length(sarr[i]));
setlength(newdata,newsize); { +1 for terminating #0 }
setlength(newdata,newsize+1);
curlen:=0; curlen:=0;
for i:=low(sarr) to high(sarr) do for i:=low(sarr) to high(sarr) do
begin begin
@ -231,7 +254,7 @@ Var
Size : SizeInt; Size : SizeInt;
begin begin
Size:=Length(S2); Size:=Length(S2);
Setlength (result,Size); Setlength(result,Size);
if Size>0 then if Size>0 then
JLSystem.ArrayCopy(JLObject(ShortstringClass(@S2).fdata),0,JLObject(AnsistringClass(result).fdata),0,Size); JLSystem.ArrayCopy(JLObject(ShortstringClass(@S2).fdata),0,JLObject(AnsistringClass(result).fdata),0,Size);
end; end;
@ -276,15 +299,17 @@ begin
exit; exit;
end; end;
foundnull:=false; foundnull:=false;
j:=0;
for i:=low(arr) to high(arr) do for i:=low(arr) to high(arr) do
if arr[i]=#0 then if arr[i]=#0 then
begin begin
foundnull:=true; foundnull:=true;
j:=i;
break; break;
end; end;
if not foundnull then if foundnull then
begin begin
res:=AnsistringClass.Create(arr); res:=AnsistringClass.Create(arr,j);
exit; exit;
end end
end end
@ -294,12 +319,13 @@ begin
exit; exit;
end; end;
res:=AnsistringClass.Create; res:=AnsistringClass.Create;
setlength(res.fdata,high(arr)+1); { +1 for terminating 0 }
setlength(res.fdata,high(arr)+2);
JLSystem.ArrayCopy(JLObject(@arr),0,JLObject(res.fdata),0,high(arr)+1); JLSystem.ArrayCopy(JLObject(@arr),0,JLObject(res.fdata),0,high(arr)+1);
result:=Ansistring(res); result:=Ansistring(res);
end; end;
procedure fpc_ansistr_to_chararray(out res: array of ansichar; const src: ansistring); compilerproc; procedure fpc_ansistr_to_chararray(out res: array of ansichar; const src: ansistring); compilerproc;
var var
len: longint; len: longint;
begin begin
@ -388,7 +414,8 @@ begin
result:=ansistring(AnsistringClass.Create) result:=ansistring(AnsistringClass.Create)
else else
result:=s; result:=s;
setlength(AnsistringClass(result).fdata,l); { +1 for terminating #0 }
setlength(AnsistringClass(result).fdata,l+1);
end; end;
{***************************************************************************** {*****************************************************************************
@ -479,7 +506,8 @@ begin
If Size>0 then If Size>0 then
begin begin
res:=AnsistringClass.Create; res:=AnsistringClass.Create;
setlength(res.fdata,size); { +1 for terminating #0 }
setlength(res.fdata,size+1);
JLSystem.ArrayCopy(JLObject(AnsistringClass(S).fdata),index,JLObject(res.fdata),0,size); JLSystem.ArrayCopy(JLObject(AnsistringClass(S).fdata),index,JLObject(res.fdata),0,size);
result:=ansistring(res); result:=ansistring(res);
end; end;

View File

@ -189,9 +189,10 @@ var
i: longint; i: longint;
begin begin
{ used to construct constant chararrays from Java string constants } { used to construct constant chararrays from Java string constants }
setlength(result,length(u)); setlength(result,length(u)+1);
for i:=1 to system.length(u) do for i:=1 to length(u) do
result[i-1]:=ansichar(ord(u[i])); result[i-1]:=ansichar(ord(u[i]));
result[length(u)]:=#0;
end; end;