mirror of
https://gitlab.com/freepascal.org/fpc/source.git
synced 2025-04-17 07:59:48 +02:00
+ implemented support for codepage aware compiler messages. It can be enabled
per platform (currently only enabled for win32 and win64). Enabling it forces code page conversion from the codepage of the .msg file to CP_ACP, before writing the message to the console. Not enabling it keeps the previous behaviour of not doing any kind of code page conversion for messages. This feature should be tested and enabled per platform, because it requires code page conversion support in the rtl (so it may require adding the appropriate extra units, such as fpwidestring). When this feature is enabled for all platforms, we can start keeping only one .msg file per language, because having extra .msg files for different encodings for the same language becomes redundant, since the compiler can do code page conversion to whatever code page the console uses. git-svn-id: trunk@36450 -
This commit is contained in:
parent
e667a18838
commit
a34f531661
@ -53,19 +53,19 @@ type
|
||||
msgidx : array[1..maxmsgidxparts] of PArrayOfPChar;
|
||||
msgidxmax : array[1..maxmsgidxparts] of longint;
|
||||
msgstates : array[1..maxmsgidxparts] of PArrayOfState;
|
||||
msgcodepage : TSystemCodePage;
|
||||
{ set if changes with $WARN need to be cleared at next module change }
|
||||
has_local_changes : boolean;
|
||||
constructor Init(n:longint;const idxmax:array of longint);
|
||||
destructor Done;
|
||||
function LoadIntern(p:pointer;n:longint):boolean;
|
||||
function LoadIntern(p:pointer;n:longint;cp:TSystemCodePage):boolean;
|
||||
function LoadExtern(const fn:string):boolean;
|
||||
procedure ClearIdx;
|
||||
procedure ResetStates;
|
||||
procedure CreateIdx;
|
||||
function GetPChar(nr:longint):pchar;
|
||||
{ function ClearVerbosity(nr:longint):boolean; not used anymore }
|
||||
function SetVerbosity(nr:longint;newstate:tmsgstate):boolean;
|
||||
function Get(nr:longint;const args:array of TMsgStr):ansistring;
|
||||
function Get(nr:longint;const args:array of TMsgStr):TMsgStr;
|
||||
end;
|
||||
|
||||
{ this will read a line until #10 or #0 and also increase p }
|
||||
@ -79,7 +79,7 @@ uses
|
||||
cutils;
|
||||
|
||||
|
||||
function MsgReplace(const s:TMsgStr;const args:array of TMsgStr):ansistring;
|
||||
function MsgReplace(const s:TMsgStr;const args:array of TMsgStr):TMsgStr;
|
||||
var
|
||||
last,
|
||||
i : longint;
|
||||
@ -117,6 +117,7 @@ begin
|
||||
has_local_changes:=false;
|
||||
msgsize:=0;
|
||||
msgparts:=n;
|
||||
msgcodepage:=CP_ACP;
|
||||
if n<>high(idxmax)+1 then
|
||||
fail;
|
||||
for i:=1 to n do
|
||||
@ -154,8 +155,9 @@ begin
|
||||
end;
|
||||
|
||||
|
||||
function TMessage.LoadIntern(p:pointer;n:longint):boolean;
|
||||
function TMessage.LoadIntern(p:pointer;n:longint;cp:TSystemCodePage):boolean;
|
||||
begin
|
||||
msgcodepage:=cp;
|
||||
msgtxt:=pchar(p);
|
||||
msgsize:=n;
|
||||
msgallocsize:=0;
|
||||
@ -185,6 +187,7 @@ var
|
||||
|
||||
begin
|
||||
LoadExtern:=false;
|
||||
msgcodepage:=CP_ACP;
|
||||
getmem(buf,bufsize);
|
||||
{ Read the message file }
|
||||
assign(f,fn);
|
||||
@ -240,6 +243,10 @@ begin
|
||||
end
|
||||
else
|
||||
err('no = found');
|
||||
end
|
||||
else if (Length(s)>11) and (Copy(s,1,11)='# CodePage ') then
|
||||
begin
|
||||
msgcodepage:=StrToInt(Copy(s,12,Length(s)-11));
|
||||
end;
|
||||
end;
|
||||
end;
|
||||
@ -398,15 +405,6 @@ begin
|
||||
end;
|
||||
|
||||
|
||||
function TMessage.GetPChar(nr:longint):pchar;
|
||||
begin
|
||||
if (nr div 1000 < msgparts) and
|
||||
(nr mod 1000 < msgidxmax[nr div 1000]) then
|
||||
GetPChar:=msgidx[nr div 1000]^[nr mod 1000]
|
||||
else
|
||||
GetPChar:='';
|
||||
end;
|
||||
|
||||
function TMessage.SetVerbosity(nr:longint;newstate:tmsgstate):boolean;
|
||||
var
|
||||
i: longint;
|
||||
@ -438,9 +436,10 @@ begin
|
||||
end;
|
||||
}
|
||||
|
||||
function TMessage.Get(nr:longint;const args:array of TMsgStr):ansistring;
|
||||
function TMessage.Get(nr:longint;const args:array of TMsgStr):TMsgStr;
|
||||
var
|
||||
hp : pchar;
|
||||
s: TMsgStr;
|
||||
begin
|
||||
if (nr div 1000 < msgparts) and
|
||||
(nr mod 1000 < msgidxmax[nr div 1000]) then
|
||||
@ -450,7 +449,14 @@ begin
|
||||
if hp=nil then
|
||||
Get:='msg nr '+tostr(nr)
|
||||
else
|
||||
Get:=MsgReplace(system.strpas(hp),args);
|
||||
begin
|
||||
s:=sysutils.StrPas(hp);
|
||||
{$ifdef cpawaremessages}
|
||||
SetCodePage(RawByteString(s),msgcodepage,False);
|
||||
SetCodePage(RawByteString(s),CP_ACP,True);
|
||||
{$endif cpawaremessages}
|
||||
Get:=MsgReplace(s,args);
|
||||
end;
|
||||
end;
|
||||
|
||||
procedure TMessage.ResetStates;
|
||||
|
@ -284,7 +284,7 @@ begin
|
||||
totaltime:=trunc(totaltime) + 1;
|
||||
timestr:=tostr(trunc(totaltime))+'.'+tostr(round(frac(totaltime)*10));
|
||||
if status.codesize<>aword(-1) then
|
||||
linkstr:=', '+tostr(status.codesize)+' ' +strpas(MessagePChar(general_text_bytes_code))+', '+tostr(status.datasize)+' '+strpas(MessagePChar(general_text_bytes_data))
|
||||
linkstr:=', '+tostr(status.codesize)+' ' +MessageStr(general_text_bytes_code)+', '+tostr(status.datasize)+' '+MessageStr(general_text_bytes_data)
|
||||
else
|
||||
linkstr:='';
|
||||
Message3(general_i_abslines_compiled,tostr(status.compiledlines),timestr,linkstr);
|
||||
|
@ -19,6 +19,14 @@
|
||||
exceptions in the constructors }
|
||||
{$IMPLICITEXCEPTIONS OFF}
|
||||
|
||||
{ This define enables codepage-aware compiler messages handling. Turning it on
|
||||
forces code page conversion from the codepage, specified in the .msg file to
|
||||
CP_ACP, before printing the message to the console. Enable this for host
|
||||
platforms, that have code page conversion support in their RTL. }
|
||||
{$if defined(win32) or defined(win64)}
|
||||
{$define cpawaremessages}
|
||||
{$endif}
|
||||
|
||||
{ Inline small functions, but not when EXTDEBUG is used }
|
||||
{$ifndef EXTDEBUG}
|
||||
{$define USEINLINE}
|
||||
|
@ -188,11 +188,13 @@ end;
|
||||
|
||||
procedure Toption.WriteLogo;
|
||||
var
|
||||
msg : TMsgStr;
|
||||
p : pchar;
|
||||
begin
|
||||
if not LogoWritten then
|
||||
begin
|
||||
p:=MessagePchar(option_logo);
|
||||
msg:=MessageStr(option_logo);
|
||||
p:=pchar(msg);
|
||||
while assigned(p) do
|
||||
Comment(V_Normal,GetMsgLine(p));
|
||||
LogoWritten:= true;
|
||||
@ -202,6 +204,7 @@ end;
|
||||
|
||||
procedure Toption.WriteInfo (More: string);
|
||||
var
|
||||
msg_str: TMsgStr;
|
||||
p : pchar;
|
||||
hs,hs1,hs3,s : TCmdStr;
|
||||
J: longint;
|
||||
@ -548,7 +551,8 @@ const
|
||||
begin
|
||||
if More = '' then
|
||||
begin
|
||||
p:=MessagePchar(option_info);
|
||||
msg_str:=MessageStr(option_info);
|
||||
p:=pchar(msg_str);
|
||||
while assigned(p) do
|
||||
begin
|
||||
s:=GetMsgLine(p);
|
||||
@ -626,6 +630,7 @@ var
|
||||
HelpLine,
|
||||
s : string;
|
||||
p : pchar;
|
||||
msg_str: TMsgStr;
|
||||
begin
|
||||
WriteLogo;
|
||||
Lines:=4;
|
||||
@ -634,7 +639,8 @@ begin
|
||||
else
|
||||
Message1(option_usage,FixFileName(system.paramstr(0)));
|
||||
lastident:=0;
|
||||
p:=MessagePChar(option_help_pages);
|
||||
msg_str:=MessageStr(option_help_pages);
|
||||
p:=pchar(msg_str);
|
||||
while assigned(p) do
|
||||
begin
|
||||
{ get a line and reset }
|
||||
|
@ -91,7 +91,7 @@ interface
|
||||
procedure GenerateError;
|
||||
procedure Internalerror(i:longint);{$ifndef VER2_6}noreturn;{$endif VER2_6}
|
||||
procedure Comment(l:longint;s:ansistring);
|
||||
function MessagePchar(w:longint):pchar;
|
||||
function MessageStr(w:longint):TMsgStr;
|
||||
procedure Message(w:longint;onqueue:tmsgqueueevent=nil);
|
||||
procedure Message1(w:longint;const s1:TMsgStr;onqueue:tmsgqueueevent=nil);
|
||||
procedure Message2(w:longint;const s1,s2:TMsgStr;onqueue:tmsgqueueevent=nil);
|
||||
@ -404,7 +404,7 @@ implementation
|
||||
{ reload the internal messages if not already loaded }
|
||||
{$ifndef EXTERN_MSG}
|
||||
if not msg^.msgintern then
|
||||
msg^.LoadIntern(@msgtxt,msgtxtsize);
|
||||
msg^.LoadIntern(@msgtxt,msgtxtsize,msgtxt_codepage);
|
||||
{$endif}
|
||||
if not msg^.LoadExtern(fn) then
|
||||
begin
|
||||
@ -412,7 +412,7 @@ implementation
|
||||
writeln('Fatal: Cannot find error message file.');
|
||||
halt(3);
|
||||
{$else}
|
||||
msg^.LoadIntern(@msgtxt,msgtxtsize);
|
||||
msg^.LoadIntern(@msgtxt,msgtxtsize,msgtxt_codepage);
|
||||
{$endif}
|
||||
end;
|
||||
{ reload the prefixes using the new messages }
|
||||
@ -756,10 +756,10 @@ implementation
|
||||
end;
|
||||
|
||||
|
||||
function MessagePchar(w:longint):pchar;
|
||||
function MessageStr(w:longint):TMsgStr;
|
||||
begin
|
||||
MaybeLoadMessageFile;
|
||||
MessagePchar:=msg^.GetPchar(w)
|
||||
MessageStr:=msg^.Get(w,[]);
|
||||
end;
|
||||
|
||||
|
||||
@ -987,7 +987,7 @@ implementation
|
||||
halt(3);
|
||||
end;
|
||||
{$ifndef EXTERN_MSG}
|
||||
msg^.LoadIntern(@msgtxt,msgtxtsize);
|
||||
msg^.LoadIntern(@msgtxt,msgtxtsize,msgtxt_codepage);
|
||||
{$else EXTERN_MSG}
|
||||
LoadMsgFile(exepath+'errore.msg');
|
||||
{$endif EXTERN_MSG}
|
||||
|
Loading…
Reference in New Issue
Block a user