J'ai une application Delphi 6 Pro qui traite les trames jpeg entrantes à partir d'un serveur vidéo en streaming. Le code fonctionne mais j'ai récemment remarqué qu'il génère un grand nombre de fautes de pages souples au fil du temps. Après quelques recherches, les fautes de page semblent provenir d'une opération graphique particulière. Notez que les bitmaps non compressés en question ont une taille de 320 x 240 ou d'environ 300 Ko, ce qui n'est pas dû à la manipulation de grandes images. Le nombre de défauts de page générés n'est pas tolérable. Plus d'une heure, il peut facilement dépasser les défauts de la page 1000000.Nombre important de fautes de page lors de l'affectation d'une image TJpegImage à un TBitmap
J'ai créé un cas de test dépouillé qui exécute le code que j'ai inclus ci-dessous sur une minuterie, 10 fois par seconde. Les erreurs de page semblent se produire lorsque j'essaie d'affecter le TJpegImage à un TBitmap dans la méthode GetBitmap(). Je le sais parce que j'ai commenté cette ligne et les fautes de page ne se produisent pas. Le assign() déclenche une opération de décompression sur la partie de TJpegImage car il pousse les bits décompressés dans un bitmap nouvellement créé que GetBitmap() renvoie. Quand je lance l'utilitaire pfmon de Microsoft (surveillance de défaut de page), j'obtiens un grand nombre de lignes d'erreurs de fautes de pages souples concernant RtlFillMemoryUlong, de sorte qu'il semble se produire lors d'une opération de remplissage de mémoire tampon.
Une note déroutante. La partie résumée du rapport de pfmon où il montre quelle DLL a causé quelle erreur de page n'affiche aucun nom de DLL dans la colonne extrême gauche. J'ai essayé cela sur un autre système et ça arrive aussi.
Quelqu'un peut-il suggérer un correctif ou une solution de contournement? Voici le code. Remarque: IReceiveBufferForClientSocket est un objet de classe simple qui contient des octets dans un tampon d'accumulation.
function GetBitmap(theJpegImage: TJpegImage): Graphics.TBitmap;
begin
Result := TBitmap.Create;
Result.Assign(theJpegImage);
end;
// ---------------------------------------------------------------
procedure processJpegFrame(intfReceiveBuffer: IReceiveBufferForClientSocket);
var
theBitmap: TBitmap;
theJpegStream, theBitmapStream: TMemoryStream;
theJpegImage: TJpegImage;
begin
theBitmap := nil;
theJpegImage := TJPEGImage.Create;
theJpegStream:= TMemoryStream.Create;
theBitmapStream := TMemoryStream.Create;
try // 2
// ************************ BEGIN JPEG FRAME PROCESSING
// Load the JPEG image from the receive buffer.
theJpegStream.Size := intfReceiveBuffer.numBytesInBuffer;
Move(intfReceiveBuffer.bufPtr^, theJpegStream.Memory^, intfReceiveBuffer.numBytesInBuffer);
theJpegImage.LoadFromStream(theJpegStream);
// Convert to bitmap.
theBitmap := GetBitmap(theJpegImage);
finally
// Free memory objects.
if Assigned(theBitmap) then
theBitmap.Free;
if Assigned(theJpegImage) then
theJpegImage.Free;
if Assigned(theBitmapStream) then
theBitmapStream.Free;
if Assigned(theJpegStream) then
theJpegStream.Free;
end; // try()
end;
// ---------------------------------------------------------------
procedure TForm1.Timer1Timer(Sender: TObject);
begin
processJpegFrame(FIntfReceiveBufferForClientSocket);
end;
// ---------------------------------------------------------------
procedure TForm1.FormCreate(Sender: TObject);
var
S: string;
begin
FIntfReceiveBufferForClientSocket := TReceiveBufferForClientSocket.Create(1000000);
S := loadStringFromFile('c:\test.jpg');
FIntfReceiveBufferForClientSocket.assign(S);
end;
// ---------------------------------------------------------------
Merci, Robert
La taille du test JPEG affecte directement le nombre de défauts de page. Avec une image JPEG d'environ 2 Ko, j'ai eu un défaut de 80 pages. Avec une image de 40 Ko, il est passé à environ 2800. Je suis sûr que la vraie relation tourne autour de la taille des images quand elles ne sont pas compressées, mais le La taille de l'image JPEG fonctionne comme un proxy grossier pour indiquer que c'est le bitmap créé dynamiquement qui génère les fautes de la page douce. –