Delphi XE2: desactivado por 7-20 líneas en los números de línea de error del depurador y compilador también desactivado por la misma cantidad
Estoy teniendo un problema con una gran base de código de Delphi donde trabajo, como un efecto secundario de la transferencia de Delphi 2007 a XE2, ahora nos encontramos con los siguientes problemas extraños y relacionados:
No puede establecer puntos de interrupción o paso a paso a través del código, incluso en la compilación de depuración, ya que la numeración de líneas está desordenada, solo en algunas de las unidades.
La introducción deliberada de un error de sintaxis en la línea 2010 hará que el cursor se enfoque en la línea 2020, con 3 o 4 líneas, algo así:
.
procedure Correct;
begin
DoSomething; // syntax error reported HERE but the real error is below.
// more stuff here.
end;
procedure OllKorrect;
begin
ThisLineIsFine();
__VARIABLE_NOT_DEFINED__ := 1; // intentional error
end
Espero que alguien haya visto esto antes. Los elementos del asunto pueden incluir:
El código contiene muchas directivas de compilación impares, como las directivas {$ REALCOMPATIBILITY ON} y {$ H -} / {$ H +}, miles de directivas {$ H +} / {$ H-} en el código.
En segundo lugar, el código utiliza una gran cantidad de directivas {$ I INCLUDE}, y sospecho que incluir archivos podría alterar directamente la numeración de líneas del compilador.
No puedo decirlo con seguridad, pero sospecho que todos los antiguos compiladores "hacen que funcione como turbo pascal para DOS" son la razón detrás de esto. Me gustaría saber si alguien sabe algo sobre esto seguro. Solo sucede en algunos lugares en el código, y con un proyecto que tiene más de 500 unidades, algunas de las cuales alcanzan un tamaño de 10K / 20KK, es definitivamente frustrante. Lo que puedo decir es que no solo las unidades que tienen directivas {$ I include.inc} estropean, y que muchas unidades que contienen una gran cantidad de directivas {$ H -} / {$ H +} o {$ REALCOMPATIBILITY} No tengo este problema. Si pudiera ver lo que las unidades que se portan mal tienen en común, podría resolver esto.
Actualización: el problema de terminación de línea tiene sentido. Corrí este código que detectó problemas. El código de corrección se comenta porque si lo descomprime y borra todo su código fuente, ese es su problema. Está cargando un archivo no Unicode en un TStringList de Unicode y lo está guardando de nuevo. Eso está bien en mi mundo porque todas las versiones están controladas y respaldadas. Su experiencia puede ser diferente.
program linefeedsProject1;
{$APPTYPE CONSOLE}
uses
IOUtils,
Classes,
Types,
SysUtils;
var
broken,notBroken:Integer;
function fix(filename:String):Boolean;
var
sl:TStringList;
begin
sl := TStringList.Create;
try
sl.LoadFromFile(filename);
//TODO:Change file extensions.
sl.SaveToFile(filename);
finally
sl.Free;
end;
end;
function scan(filename:String):Boolean;
var
crFlag:Boolean;
lfFlag:Boolean;
missingCr:Integer;
missingLf:Integer;
f:TFileStream;
buf:Array[0..1024] of AnsiChar;
n:Integer;
procedure scanChars;
var
i:Integer;
begin
for i := 0 to n-1 do
begin
if buf[i]=#13 then
begin
crFlag := true;
lfFlag := false;
end
else if buf[i]=#10 then
begin
if not crFlag then
inc(missingCr);
lfFlag := true;
crFlag := false;
end
else begin
if (crFlag) then
inc(missingLf);
crFlag := false;
lfFlag := false;
end;
end;
end;
begin
result := false;
crFlag := false;
lfFlag := false;
missingCr := 0;
missingLf := 0;
f := TFileStream.Create(filename, fmOpenRead);
try
while f.Position< f.Size do
begin
n := f.Read(buf[0],1024);
scanChars;
end;
if (missingCr>0) or (missingLf>0) then
begin
WriteLn(' ', filename);
Inc(broken);
result := true;
end
else
begin
Inc(notBroken);
end
finally
f.Free;
end;
end;
var
files:TStringDynArray;
afile:String;
begin
try
broken := 0;
notBroken := 0;
files := TDirectory.GetFiles('C:\dev\abackupcopyofyoursourcecode', '*.pas',
TSearchOption.soTopDirectoryOnly );
// tried TSearchOption.soAllDirectories and it exploded. not recommended.
for afile in files do
begin
if scan(afile) then
begin
// fix(afile); // uncomment at your own risk and only on a backup copy of your code.
end;
end;
WriteLn('Broken ', broken);
WriteLn('not broken ',notBroken);
// readln;
except
on E: Exception do
Writeln(E.ClassName, ': ', E.Message);
end;
end.
Actualización 2: Si desea un escáner / reparador para este problema, puede descargar el mío (con la fuente) aquí. El enlace es Google Drive. Puede ver el código fuente desde el enlace, pero haga clic en el menú desplegable "Archivo" (parte de la interfaz de usuario web de Google Drive) y luego haga clic en "Descargar" para descargarlo.