mirror of
https://gitlab.com/freepascal.org/lazarus/lazarus.git
synced 2025-07-28 18:36:18 +02:00
PoChecker:
* don't skip formatting errors check even if translated string has no formatting arguments at all; * rewrite formatting arguments comparison function in order to make it more robust and detect invalid formatting arguments; * report formatting error even if arguments match, but some of them are invalid (only skip the case when original and translated strings exactly match, to not report e.g. '{%Region}' string); * regenerated translations, updated Russian translation. git-svn-id: trunk@39771 -
This commit is contained in:
parent
a4f6c3035e
commit
97a96b51f1
@ -1,7 +1,7 @@
|
|||||||
# Arabic translation of Free Pascal Lazarus Project.
|
Arabic translation of Free Pascal Lazarus Project.
|
||||||
# Copyright (C) 2012 Lazarus Project
|
Copyright (C) 2012 Lazarus Project
|
||||||
# This file is distributed under the same license as the Lazarus package.
|
This file is distributed under the same license as the Lazarus package.
|
||||||
# Khaled Shagrouni <shagrouni@gmail.com>, 2012.
|
Khaled Shagrouni <shagrouni@gmail.com>, 2012.
|
||||||
msgid ""
|
msgid ""
|
||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: Free Pascal Lazarus Project.\n"
|
"Project-Id-Version: Free Pascal Lazarus Project.\n"
|
||||||
@ -108,7 +108,9 @@ msgid "Identifier [%s] not found in %s"
|
|||||||
msgstr "المعرّف [%s] لم يتّم إيجاده في %s"
|
msgstr "المعرّف [%s] لم يتّم إيجاده في %s"
|
||||||
|
|
||||||
#: pocheckerconsts.sincompatibleformatargs
|
#: pocheckerconsts.sincompatibleformatargs
|
||||||
msgid "[Line: %d] Incompatible format() arguments for:"
|
#, fuzzy
|
||||||
|
#| msgid "[Line: %d] Incompatible format() arguments for:"
|
||||||
|
msgid "[Line: %d] Incompatible and/or invalid format() arguments for:"
|
||||||
msgstr "[السطر: %d] معطيات format() غير متوافقة ل:"
|
msgstr "[السطر: %d] معطيات format() غير متوافقة ل:"
|
||||||
|
|
||||||
#: pocheckerconsts.slineinfilename
|
#: pocheckerconsts.slineinfilename
|
||||||
@ -207,4 +209,5 @@ msgstr "الترجمة"
|
|||||||
|
|
||||||
#: pocheckerconsts.sunselectalltests
|
#: pocheckerconsts.sunselectalltests
|
||||||
msgid "Unselect all tests"
|
msgid "Unselect all tests"
|
||||||
msgstr "إزالة اختيار كل الإختبارات"
|
msgstr "إزالة اختيار كل الإختبارات"
|
||||||
|
|
||||||
|
@ -101,7 +101,9 @@ msgid "Identifier [%s] not found in %s"
|
|||||||
msgstr "Identifikátor [%s] nenalezen v %s"
|
msgstr "Identifikátor [%s] nenalezen v %s"
|
||||||
|
|
||||||
#: pocheckerconsts.sincompatibleformatargs
|
#: pocheckerconsts.sincompatibleformatargs
|
||||||
msgid "[Line: %d] Incompatible format() arguments for:"
|
#, fuzzy
|
||||||
|
#| msgid "[Line: %d] Incompatible format() arguments for:"
|
||||||
|
msgid "[Line: %d] Incompatible and/or invalid format() arguments for:"
|
||||||
msgstr "[Řádek %d] Nekompatibilní argumenty fce format() pro:"
|
msgstr "[Řádek %d] Nekompatibilní argumenty fce format() pro:"
|
||||||
|
|
||||||
#: pocheckerconsts.slineinfilename
|
#: pocheckerconsts.slineinfilename
|
||||||
|
@ -91,7 +91,7 @@ msgid "Identifier [%s] not found in %s"
|
|||||||
msgstr "Bezeichner [%s] nicht gefunden in %s"
|
msgstr "Bezeichner [%s] nicht gefunden in %s"
|
||||||
|
|
||||||
#: pocheckerconsts.sincompatibleformatargs
|
#: pocheckerconsts.sincompatibleformatargs
|
||||||
msgid "[Line: %d] Incompatible format() arguments for:"
|
msgid "[Line: %d] Incompatible and/or invalid format() arguments for:"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
#: pocheckerconsts.slineinfilename
|
#: pocheckerconsts.slineinfilename
|
||||||
|
@ -63,7 +63,7 @@ msgstr "[Línea %d] %s"
|
|||||||
|
|
||||||
#: pocheckerconsts.sduplicateoriginals
|
#: pocheckerconsts.sduplicateoriginals
|
||||||
msgid "The (untranslated) value \"%s\" is used for more than 1 entry:"
|
msgid "The (untranslated) value \"%s\" is used for more than 1 entry:"
|
||||||
msgstr "El valor (sin traducir) \"%s\ " se utiliza para más de 1 entrada:"
|
msgstr "El valor (sin traducir) \"%s \" se utiliza para más de 1 entrada:"
|
||||||
|
|
||||||
#: pocheckerconsts.serroroncleanup
|
#: pocheckerconsts.serroroncleanup
|
||||||
msgid ""
|
msgid ""
|
||||||
@ -71,8 +71,8 @@ msgid ""
|
|||||||
"%s\n"
|
"%s\n"
|
||||||
"Please close the program\n"
|
"Please close the program\n"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
"A ocurrido\n un error irrecuperable"
|
"A ocurrido\n"
|
||||||
"%s\n"
|
" un error irrecuperable%s\n"
|
||||||
"Por favor, cierre la program\n"
|
"Por favor, cierre la program\n"
|
||||||
|
|
||||||
#: pocheckerconsts.serroroncreate
|
#: pocheckerconsts.serroroncreate
|
||||||
@ -100,7 +100,9 @@ msgid "Identifier [%s] not found in %s"
|
|||||||
msgstr "Identificador [%s] no se encuentra en %s"
|
msgstr "Identificador [%s] no se encuentra en %s"
|
||||||
|
|
||||||
#: pocheckerconsts.sincompatibleformatargs
|
#: pocheckerconsts.sincompatibleformatargs
|
||||||
msgid "[Line: %d] Incompatible format() arguments for:"
|
#, fuzzy
|
||||||
|
#| msgid "[Line: %d] Incompatible format() arguments for:"
|
||||||
|
msgid "[Line: %d] Incompatible and/or invalid format() arguments for:"
|
||||||
msgstr "[Línea: %d] format() argumentos incompatibles para:"
|
msgstr "[Línea: %d] format() argumentos incompatibles para:"
|
||||||
|
|
||||||
#: pocheckerconsts.slineinfilename
|
#: pocheckerconsts.slineinfilename
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
# Valdas Jankunas <zmuogs@gmail.com>, 2012.
|
Valdas Jankunas <zmuogs@gmail.com>, 2012.
|
||||||
msgid ""
|
msgid ""
|
||||||
msgstr ""
|
msgstr ""
|
||||||
"Content-Type: text/plain; charset=UTF-8\n"
|
"Content-Type: text/plain; charset=UTF-8\n"
|
||||||
@ -9,8 +9,7 @@ msgstr ""
|
|||||||
"Language: lt\n"
|
"Language: lt\n"
|
||||||
"Content-Transfer-Encoding: 8bit\n"
|
"Content-Transfer-Encoding: 8bit\n"
|
||||||
"MIME-Version: 1.0\n"
|
"MIME-Version: 1.0\n"
|
||||||
"Plural-Forms: nplurals=3; plural=(n%10==1 && n%100!=11 ? 0 : n%10>=2 && (n%"
|
"Plural-Forms: nplurals=3; plural=(n%10==1 && n%100!=11 ? 0 : n%10>=2 && (n%100<10 || n%100>=20) ? 1 : 2);\n"
|
||||||
"100<10 || n%100>=20) ? 1 : 2);\n"
|
|
||||||
"X-Generator: Lokalize 1.5\n"
|
"X-Generator: Lokalize 1.5\n"
|
||||||
|
|
||||||
#: pocheckerconsts.rspochecker
|
#: pocheckerconsts.rspochecker
|
||||||
@ -104,7 +103,9 @@ msgid "Identifier [%s] not found in %s"
|
|||||||
msgstr "Ieškota identifikatoriaus [%s], tačiau %s jo neturi"
|
msgstr "Ieškota identifikatoriaus [%s], tačiau %s jo neturi"
|
||||||
|
|
||||||
#: pocheckerconsts.sincompatibleformatargs
|
#: pocheckerconsts.sincompatibleformatargs
|
||||||
msgid "[Line: %d] Incompatible format() arguments for:"
|
#, fuzzy
|
||||||
|
#| msgid "[Line: %d] Incompatible format() arguments for:"
|
||||||
|
msgid "[Line: %d] Incompatible and/or invalid format() arguments for:"
|
||||||
msgstr "[Eilutė: %d] Nesuderinamų „format()“ argumentų turi:"
|
msgstr "[Eilutė: %d] Nesuderinamų „format()“ argumentų turi:"
|
||||||
|
|
||||||
#: pocheckerconsts.slineinfilename
|
#: pocheckerconsts.slineinfilename
|
||||||
@ -205,4 +206,3 @@ msgstr "Vertimas"
|
|||||||
msgid "Unselect all tests"
|
msgid "Unselect all tests"
|
||||||
msgstr "Naikinti testavimų žymėjimą"
|
msgstr "Naikinti testavimų žymėjimą"
|
||||||
|
|
||||||
|
|
||||||
|
@ -83,7 +83,7 @@ msgid "Identifier [%s] not found in %s"
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
#: pocheckerconsts.sincompatibleformatargs
|
#: pocheckerconsts.sincompatibleformatargs
|
||||||
msgid "[Line: %d] Incompatible format() arguments for:"
|
msgid "[Line: %d] Incompatible and/or invalid format() arguments for:"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
#: pocheckerconsts.slineinfilename
|
#: pocheckerconsts.slineinfilename
|
||||||
|
@ -19,7 +19,7 @@ msgid ""
|
|||||||
"%s\n"
|
"%s\n"
|
||||||
"for selected file\n"
|
"for selected file\n"
|
||||||
"%s\n"
|
"%s\n"
|
||||||
msgstr "Impossível localizar o arquivo po mestre:\n"
|
msgstr "Impossível localizar o arquivo po mestre:"
|
||||||
|
|
||||||
#: pocheckerconsts.scheckforduplicateuntranslatedvalues
|
#: pocheckerconsts.scheckforduplicateuntranslatedvalues
|
||||||
msgid "Check for duplicate untranslated values"
|
msgid "Check for duplicate untranslated values"
|
||||||
@ -66,13 +66,13 @@ msgid ""
|
|||||||
"An unrecoverable error occurred\n"
|
"An unrecoverable error occurred\n"
|
||||||
"%s\n"
|
"%s\n"
|
||||||
"Please close the program\n"
|
"Please close the program\n"
|
||||||
msgstr "Ocorreu um erro irrecuperável\n"
|
msgstr "Ocorreu um erro irrecuperável"
|
||||||
|
|
||||||
#: pocheckerconsts.serroroncreate
|
#: pocheckerconsts.serroroncreate
|
||||||
msgid ""
|
msgid ""
|
||||||
"Error creating an instance of TPoFamily:\n"
|
"Error creating an instance of TPoFamily:\n"
|
||||||
"%s\n"
|
"%s\n"
|
||||||
msgstr "Erro ao criar uma instância de TPoFamily:\n"
|
msgstr "Erro ao criar uma instância de TPoFamily:"
|
||||||
|
|
||||||
#: pocheckerconsts.serrorsbytest
|
#: pocheckerconsts.serrorsbytest
|
||||||
msgid "Errors / warnings reported by %s for:"
|
msgid "Errors / warnings reported by %s for:"
|
||||||
@ -91,7 +91,9 @@ msgid "Identifier [%s] not found in %s"
|
|||||||
msgstr "Identificador [%s] não encontrado em %s"
|
msgstr "Identificador [%s] não encontrado em %s"
|
||||||
|
|
||||||
#: pocheckerconsts.sincompatibleformatargs
|
#: pocheckerconsts.sincompatibleformatargs
|
||||||
msgid "[Line: %d] Incompatible format() arguments for:"
|
#, fuzzy
|
||||||
|
#| msgid "[Line: %d] Incompatible format() arguments for:"
|
||||||
|
msgid "[Line: %d] Incompatible and/or invalid format() arguments for:"
|
||||||
msgstr "[Linha: %d] formato() incompatível de argumentos para:"
|
msgstr "[Linha: %d] formato() incompatível de argumentos para:"
|
||||||
|
|
||||||
#: pocheckerconsts.slineinfilename
|
#: pocheckerconsts.slineinfilename
|
||||||
|
@ -100,8 +100,9 @@ msgid "Identifier [%s] not found in %s"
|
|||||||
msgstr "Идентификатор [%s] не найден в %s"
|
msgstr "Идентификатор [%s] не найден в %s"
|
||||||
|
|
||||||
#: pocheckerconsts.sincompatibleformatargs
|
#: pocheckerconsts.sincompatibleformatargs
|
||||||
msgid "[Line: %d] Incompatible format() arguments for:"
|
#| msgid "[Line: %d] Incompatible format() arguments for:"
|
||||||
msgstr "[Строка: %d] Несовместимые аргументы для Format() в:"
|
msgid "[Line: %d] Incompatible and/or invalid format() arguments for:"
|
||||||
|
msgstr "[Строка: %d] Несовместимые и/или неверные аргументы для Format() в:"
|
||||||
|
|
||||||
#: pocheckerconsts.slineinfilename
|
#: pocheckerconsts.slineinfilename
|
||||||
msgid "[Line %d] in %s:"
|
msgid "[Line %d] in %s:"
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
# Igor Paliychuk <mansonigor@gmail.com>, 2012.
|
Igor Paliychuk <mansonigor@gmail.com>, 2012.
|
||||||
msgid ""
|
msgid ""
|
||||||
msgstr ""
|
msgstr ""
|
||||||
"PO-Revision-Date: 2012-04-23 11:40+0300\n"
|
"PO-Revision-Date: 2012-04-23 11:40+0300\n"
|
||||||
@ -6,8 +6,7 @@ msgstr ""
|
|||||||
"Language: uk\n"
|
"Language: uk\n"
|
||||||
"Content-Type: text/plain; charset=UTF-8\n"
|
"Content-Type: text/plain; charset=UTF-8\n"
|
||||||
"Content-Transfer-Encoding: 8bit\n"
|
"Content-Transfer-Encoding: 8bit\n"
|
||||||
"Plural-Forms: nplurals=3; plural=(n%10==1 && n%100!=11 ? 0 : n%10>=2 && n%"
|
"Plural-Forms: nplurals=3; plural=(n%10==1 && n%100!=11 ? 0 : n%10>=2 && n%10<=4 && (n%100<10 || n%100>=20) ? 1 : 2);\n"
|
||||||
"10<=4 && (n%100<10 || n%100>=20) ? 1 : 2);\n"
|
|
||||||
"X-Generator: Virtaal 0.7.1\n"
|
"X-Generator: Virtaal 0.7.1\n"
|
||||||
|
|
||||||
#: pocheckerconsts.rspochecker
|
#: pocheckerconsts.rspochecker
|
||||||
@ -24,7 +23,7 @@ msgstr ""
|
|||||||
"Не можу знайти основний po файл:\n"
|
"Не можу знайти основний po файл:\n"
|
||||||
"%s\n"
|
"%s\n"
|
||||||
"для вибраного файлу\n"
|
"для вибраного файлу\n"
|
||||||
"%s"
|
"%s\n"
|
||||||
|
|
||||||
#: pocheckerconsts.scheckforduplicateuntranslatedvalues
|
#: pocheckerconsts.scheckforduplicateuntranslatedvalues
|
||||||
msgid "Check for duplicate untranslated values"
|
msgid "Check for duplicate untranslated values"
|
||||||
@ -101,7 +100,9 @@ msgid "Identifier [%s] not found in %s"
|
|||||||
msgstr "Ідентифікатор [%s] не знайдений в %s"
|
msgstr "Ідентифікатор [%s] не знайдений в %s"
|
||||||
|
|
||||||
#: pocheckerconsts.sincompatibleformatargs
|
#: pocheckerconsts.sincompatibleformatargs
|
||||||
msgid "[Line: %d] Incompatible format() arguments for:"
|
#, fuzzy
|
||||||
|
#| msgid "[Line: %d] Incompatible format() arguments for:"
|
||||||
|
msgid "[Line: %d] Incompatible and/or invalid format() arguments for:"
|
||||||
msgstr "[Рядок: %d] Несумісні аргументи format() для:"
|
msgstr "[Рядок: %d] Несумісні аргументи format() для:"
|
||||||
|
|
||||||
#: pocheckerconsts.slineinfilename
|
#: pocheckerconsts.slineinfilename
|
||||||
@ -201,3 +202,4 @@ msgstr "Переклад"
|
|||||||
#: pocheckerconsts.sunselectalltests
|
#: pocheckerconsts.sunselectalltests
|
||||||
msgid "Unselect all tests"
|
msgid "Unselect all tests"
|
||||||
msgstr "Зняти вибір з всіх тестів"
|
msgstr "Зняти вибір з всіх тестів"
|
||||||
|
|
||||||
|
@ -44,7 +44,7 @@ resourcestring
|
|||||||
sCheckForDuplicateUntranslatedValues = 'Check for duplicate untranslated '
|
sCheckForDuplicateUntranslatedValues = 'Check for duplicate untranslated '
|
||||||
+'values';
|
+'values';
|
||||||
sFindAllTranslatedPoFiles = 'Find all translated po-files';
|
sFindAllTranslatedPoFiles = 'Find all translated po-files';
|
||||||
sIncompatibleFormatArgs = '[Line: %d] Incompatible format() arguments for:' ;
|
sIncompatibleFormatArgs = '[Line: %d] Incompatible and/or invalid format() arguments for:' ;
|
||||||
|
|
||||||
sNrErrorsFound = 'Found %d errors.';
|
sNrErrorsFound = 'Found %d errors.';
|
||||||
sNrWarningsFound = 'Found %d warnings.';
|
sNrWarningsFound = 'Found %d warnings.';
|
||||||
|
@ -78,7 +78,7 @@ Type
|
|||||||
property OnTestEnd: TTestEndEvent read FOnTestEnd write FOnTestEnd;
|
property OnTestEnd: TTestEndEvent read FOnTestEnd write FOnTestEnd;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function ExtractFormatArgs(S: String): String;
|
function ExtractFormatArgs(S: String; out ArgumentError: boolean): String;
|
||||||
function IsMasterPoName(const Fn: String): Boolean;
|
function IsMasterPoName(const Fn: String): Boolean;
|
||||||
function ExtractMasterNameFromChildName(const AChildName: String): String;
|
function ExtractMasterNameFromChildName(const AChildName: String): String;
|
||||||
function FindAllTranslatedPoFiles(const Filename: string): TStringList;
|
function FindAllTranslatedPoFiles(const Filename: string): TStringList;
|
||||||
@ -114,42 +114,42 @@ const
|
|||||||
|
|
||||||
//Helper functions
|
//Helper functions
|
||||||
|
|
||||||
function ExtractFormatArgs(S: String): String;
|
function ExtractFormatArgs(S: String; out ArgumentError: boolean): String;
|
||||||
const
|
const
|
||||||
FormatSpecs = ['D','E','F','G','M','N','P','S','U','X'];
|
FormatArgs = 'DEFGMNPSUX';
|
||||||
|
FormatChar = '%';
|
||||||
|
FormatSpecs = ':-.0123456789';
|
||||||
var
|
var
|
||||||
i,p: Integer;
|
p: PtrInt;
|
||||||
InFormat: Boolean;
|
NewStr, Symb: String;
|
||||||
NewStr: String;
|
|
||||||
c: Char;
|
|
||||||
begin
|
begin
|
||||||
SetLength(NewStr, Length(S));
|
NewStr := '';
|
||||||
InFormat := False;
|
ArgumentError := false;
|
||||||
p := 0;
|
p := UTF8Pos(FormatChar, S);
|
||||||
for i := 1 to length(S) do
|
while (Length(S)>0) and (p>0) do
|
||||||
begin
|
begin
|
||||||
c := S[i];
|
UTF8Delete(S, 1, p);
|
||||||
if (c = '%') then InFormat := not InFormat;
|
if Length(S)>0 then
|
||||||
//debugln('i = ',dbgs(i),' c = ',c,' InFormat = ',dbgs(informat));
|
|
||||||
if InFormat and (UpCase(c) in (FormatSpecs+['%'])) then
|
|
||||||
begin
|
begin
|
||||||
|
Symb := UTF8UpperCase(UTF8Copy(S, 1, 1));
|
||||||
|
while (Length(S)>1) and (UTF8Pos(Symb, FormatSpecs)>0) do
|
||||||
begin
|
begin
|
||||||
Inc(p);
|
//weak syntax check for formatting options, skip them if found
|
||||||
NewStr[p] := c;
|
UTF8Delete(S, 1, 1);
|
||||||
|
Symb := UTF8UpperCase(UTF8Copy(S, 1, 1));
|
||||||
end;
|
end;
|
||||||
end
|
if Symb <> FormatChar then
|
||||||
else
|
begin
|
||||||
begin
|
NewStr := NewStr+Symb;
|
||||||
if (c = '%') and (i > 1) and (S[i-1] = '%') and (p > 0) and (NewStr[p] = '%') then
|
if UTF8Pos(Symb, FormatArgs)=0 then
|
||||||
begin//2 consecutive % means a literal % and is not a format specifier
|
ArgumentError := true;
|
||||||
//debugln('p = ',dbgs(p), 'i = ',dbgs(i));
|
|
||||||
NewStr[p] := '#';
|
|
||||||
Dec(p);
|
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
if InFormat and (Upcase(c) in FormatSpecs) then InFormat := False;
|
//removing processed symbol
|
||||||
|
UTF8Delete(S, 1, 1);
|
||||||
|
//searching for next argument
|
||||||
|
p := UTF8Pos(FormatChar, S);
|
||||||
end;
|
end;
|
||||||
SetLength(NewStr, p);
|
|
||||||
Result := NewStr;
|
Result := NewStr;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
@ -226,8 +226,18 @@ end;
|
|||||||
|
|
||||||
|
|
||||||
function CompareFormatArgs(S1, S2: String): Boolean;
|
function CompareFormatArgs(S1, S2: String): Boolean;
|
||||||
|
var
|
||||||
|
ArgErr1, ArgErr2: boolean;
|
||||||
begin
|
begin
|
||||||
Result := CompareText(ExtractFormatArgs(S1), ExtractFormatArgs(S2)) = 0;
|
Result := true;
|
||||||
|
//do not check arguments if strings are equal to save time and avoid some
|
||||||
|
//false positives, e.g. for '{%Region}' string in lazarusidestrconsts
|
||||||
|
if S1 <> S2 then
|
||||||
|
begin
|
||||||
|
Result := CompareText(ExtractFormatArgs(S1, ArgErr1), ExtractFormatArgs(S2, ArgErr2)) = 0;
|
||||||
|
//setting result to false if invalid arguments were found even if the match
|
||||||
|
Result := Result and not ArgErr1 and not ArgErr2;
|
||||||
|
end;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{ TPoFamily }
|
{ TPoFamily }
|
||||||
@ -347,7 +357,7 @@ begin
|
|||||||
//CPoItem := FChild.FindPoItem(MPoItem.Identifier);
|
//CPoItem := FChild.FindPoItem(MPoItem.Identifier);
|
||||||
if Assigned(CPoItem) then
|
if Assigned(CPoItem) then
|
||||||
begin
|
begin
|
||||||
if (Pos('%', CPoItem.Translation) > 0) and not CompareFormatArgs(CPoItem.Original, CPoItem.Translation) then
|
if CompareFormatArgs(CPoItem.Original, CPoItem.Translation) = false then
|
||||||
begin
|
begin
|
||||||
if (ErrorCount = 0) then
|
if (ErrorCount = 0) then
|
||||||
begin
|
begin
|
||||||
|
Loading…
Reference in New Issue
Block a user