Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Win32/Win64 API (native code) (https://www.delphipraxis.net/17-win32-win64-api-native-code/)
-   -   Delphi RenFile (https://www.delphipraxis.net/128275-renfile.html)

Willie1 27. Jan 2009 11:13


RenFile
 
Hallo Leute,

der folgende Code löst unter Vista eine "Zugriffsverletzung ... in Modul 'Kernel32.dll' lesen von Adresse 2" aus, unter W98 ist alles in Ordnung.
Woran kann das liegen? Ist RenFile bei Vista geändert worden?
Delphi-Quellcode:
  if MessageDlg(s,mtConfirmation,[mbYes,MbNo,mbHelp],10) = mrYes then begin
    if RenFile(Oldname,Bli.Folder + Newname) then // <--- HIER ------------
    begin
      if Config.CBit[Ord(Confirm)] then ShowMessage('Neuer Namen: "' + Newname + '"');
      BLi.Bildnamen[Bildpos]:=Newname;
      Renamed:=true
    end
  end;
MfG
Willie1

Luckie 27. Jan 2009 11:16

Re: RenFile
 
Was ist den RenFile? Von der Funktion habe ich noch nichts gehört, weder unter Delphi noch kenne ich sie aus der WinAPI.

Und bitte editier deinen Beitrag und ihm einen aussagekräftigeren Titel.

Klaus01 27. Jan 2009 11:21

Re: RenFile
 
Guten Morgen,

RenFile, ist das eine Win-Api Routine?


Tritt das Problem bei allen möglichen Dateien auf?
Oder tritt es nur bei bestimmten Dateien/Verzeichnissen auf?

Grüße
Klaus

Willie1 27. Jan 2009 11:40

Umbenennen von Files mit Windows
 
Sorry, ich habe meine Frage mit "zu heißer Nadel gestrickt"!

Eigene Funktion RenFile sieht so aus:

Delphi-Quellcode:
  function RenFile(const Oldname,Newname: string): Boolean;
  var
    SHFOS: TSHFileOpStruct;
    a,n: array[0..255] of Char;
  begin
    if FileExists(Oldname) then begin
      FillChar(a, SizeOf(a), 0);
      StrPCopy(a, ExpandFilename(Oldname)+#0#0);
      FillChar(n, SizeOf(n), 0);
      StrPCopy(n, ExpandFilename(Newname)+#0#0);
      with SHFOS do begin
        Wnd:=0;
        wFunc:=FO_RENAME;
        pFrom:=a;
        pTo:=n;
        fFlags:=FOF_SIMPLEPROGRESS;
        fAnyOperationsAborted:=false;
        hNameMappings:=nil;
      end;
      Result:=(ShFileOperation(SHFOS) = 0) and
              (SHFOS.fAnyOperationsAborted = LongBool(false)) and FileExists(NewName)
    end
    else
      Result:=false
  end; {RenFile}
Der Fehler tritt bei beliebigen Dateien und Pfaden nur unter Vista auf.

Luckie 27. Jan 2009 11:44

Re: RenFile
 
Und an welcher Stelle in der Funktion tritt die Zugriffsverletzung genau auf? Und welche Entwicklungsumgebung wird genutzt?

Und der Titel ist immer noch recht unbefriedigend. Vorschlag: "Datei umbenennen mit ShFileOperation schlägt unter Vista fehl"

himitsu 27. Jan 2009 11:50

Re: RenFile
 
auch wen es nicht DER Fehler ist

Delphi-Quellcode:
// statt
(SHFOS.fAnyOperationsAborted = LongBool(false))

// lieber
not SHFOS.fAnyOperationsAborted
LongBool(false) ist zwar immer 0, aber LongBool(true) ... nja, vorallem für die WinAPI ist =LongBool(true) nicht immer das Selbe

Klaus01 27. Jan 2009 12:00

Re: RenFile
 
.. mag das eventuell damit etwas zu tun haben:


There are two versions of this structure, an ANSI version (SHFILEOPSTRUCTA) and a Unicode version (SHFILEOPSTRUCTW). The Unicode version is identical to the ANSI version, except that wide character strings (LPCWSTR) are used in place of ANSI character strings (LPCSTR). On Microsoft Windows 98 and earlier, only the ANSI version is supported. On Microsoft Windows NT 4.0 and later, both the ANSI and Unicode versions of this structure are supported. SHFILEOPSTRUCTW and SHFILEOPTSTRUCTA should never be used directly; the appropriate structure is redefined as SHFILEOPSTRUCT by the precompiler depending on whether the application is compiled for ANSI or Unicode.
SHNAMEMAPPING has similar ANSI and Unicode versions. For ANSI applications, hNameMappings points to an int followed by an array of ANSI SHNAMEMAPPING structures. For Unicode applications, hNameMappings points to an int followed by an array of Unicode SHNAMEMAPPING structures. However, on Windows NT 4.0 and later, SHFileOperation always returns a handle to a Unicode set of SHNAMEMAPPING structures. If you want applications to be functional with all versions of Windows, the application must employ conditional code to deal with name mappings. For example:

Copy Code
Code:
x = SHFileOperation(&shop);

if (fWin9x)
   HandleAnsiNameMappings(shop.hNameMappings);
else
   HandleUnicodeNameMappings(shop.hNameMappings);
Treat hNameMappings as a pointer to a structure whose members are a UINT value followed by a pointer to an array of SHNAMEMAPPING structures, as seen in its declaration:


Quelle

Grüße
Klaus

himitsu 27. Jan 2009 12:15

Re: RenFile
 
es kommt dann darauf an, welche Version Delphi aufruft.

die WinAPI kennt SHFileOperation garnicht
Delphi 2009 leitet SHFileOperation nach SHFileOperationW um
und alles andere nach SHFileOperationA

SHFileOperationA ist ANSI
und SHFileOperationW demnach Unicode

ja und Win98 kennt standardmäßig kein Unicode (aber da sollte das Programm garnicht erst starten, wenn SHFileOperationW fest eingebunden ist, da dort der ProgrammLoader meckern sollte)

Willie1 27. Jan 2009 12:18

Re: RenFile
 
Luckie,
ich benutze die Bibliothek GDIAPI von http://www.progdigy.com, die sich nach meinem jetzigen Kenntisstand nur mit D6/7 kompilieren lässt. Das hat aber mit dem Problem nichts zu tun.

Also Delphi 6.

Ich werde mit euren Tipps (Danke Klaus + himitsu) versuchen das Problem zu lösen und melde mich später nochmal.

Gruß W.

Progman 27. Jan 2009 12:56

Re: RenFile
 
Warum wird nicht die Function RenameFile() genutzt? Die ist (mind.) ab Delphi6 in allen Delphi-Versionen vorhanden und geht auch unter Vista, bei vorhanden Schreibrechten)

Klaus01 27. Jan 2009 13:09

Re: RenFile
 
Zitat:

Zitat von Progman
Warum wird nicht die Function RenameFile() genutzt? Die ist (mind.) ab Delphi6 in allen Delphi-Versionen vorhanden und geht auch unter Vista, bei vorhanden Schreibrechten)

Weil ihm das hier nicht viel bringen wird.
RenameFile ruft moveFile auf.
Laut msdn wird da mindestens Windows 2000 benötigt.
Quelle

Grüße
Klaus

Andreas L. 27. Jan 2009 13:12

Re: RenFile
 
Vllt. fehlt dir ein Backslash:

Delphi-Quellcode:
if RenFile(Oldname, IncludeTrailingPathDelimiter(Bli.Folder) + Newname) then

Willie1 27. Jan 2009 18:40

Datei umben mit ShFileOperation schlägt unter Vista fehl
 
Ich habe die Routine, wie folgt geändert:

Delphi-Quellcode:
  function RenFile(const Oldname,Newname: string): Boolean;
  var
    SHFOS: TSHFileOpStruct;
    o,n: string;
  begin
    if FileExists(Oldname) then begin
      o:=Oldname + #0#0;
      n:=Newname + #0#0;
      with SHFOS do begin
        Wnd:=0;
        wFunc:=FO_RENAME;
        pFrom:=PChar(o);
        pTo:=PChar(n);
        fFlags:=FOF_SIMPLEPROGRESS;
        fAnyOperationsAborted:=false;
        hNameMappings:=nil;
      end;
      Result:=(ShFileOperation(SHFOS) = 0) and
               not SHFOS.fAnyOperationsAborted and FileExists(NewName)
    end
    else
      Result:=false
  end; {RenFile}
Jetzt tritt bei Vista dieselbe Zugriffsverletzung an einer anderen Stelle auf. Bei W98 ist alles ok, muss hier wirklich zwischen >W98 und <=W98 unterschieden werden, wie ist es mit ME?

Willie

Luckie 27. Jan 2009 19:59

Re: RenFile
 
Der Thread hat ja immer noch den gleichen nicht aussgaekräftigen Titel, dabei habe ich selbst einen besseren vorgeschlagen. Bitte ändere das noch.

Klaus01 27. Jan 2009 21:11

Re: Datei umben mit ShFileOperation schlägt unter Vista fehl
 
Zitat:

Zitat von Willie1

Jetzt tritt bei Vista dieselbe Zugriffsverletzung an einer anderen Stelle auf. Bei W98 ist alles ok, muss hier wirklich zwischen >W98 und <=W98 unterschieden werden, wie ist es mit ME?

Willie

Guten Abend Willie,

kompilierst Du unter win98 und läßt das Programm auf Vista laufen?

Wenn ich Deine Routine unter XP kompiliere und laufen lassen, wirft sie keine Fehlermeldung.
Ich habe kein Win98 und kein Vista um diese Kombination zu testen.

Grüße
Klaus

Willie1 28. Jan 2009 17:11

Re: RenFile
 
Hallo Klaus,
ich sehe, du bist online.
Ja ich kompiliere wegen einer bestimmten Bibliothek (GDIAPI) mit D6 auf W98 und lasse es mit W98 und Vista laufen.
Das Programm ist nicht neu, der Fehler wäre mir bestimmt früher aufgefallen!!! Ich habe es gestern Abend nochmal ausprobiert, mal gibt es die Zugriffsverletztung dann wieder nicht. Die genaue Absturzstelle kenne ich nicht, weil der Fehler bei D6 u. W98 nicht auftritt.

Hier noch einmal die Routine (sie ist ja weiß Gott nicht besonders). Ich benutze sie so oft, dass ich glaubte, sie gehörte zu Delphi :
Delphi-Quellcode:
function RenFile(const Oldname,Newname: string): Boolean;
  var
    SHFOS: TSHFileOpStruct;
    o,n: string;
  begin
    if FileExists(Oldname) then begin
      o:=Oldname + #0#0;
      n:=Newname + #0#0;
      with SHFOS do begin
        Wnd:=0;
        wFunc:=FO_RENAME;
        pFrom:=PChar(o);
        pTo:=PChar(n);
        fFlags:=FOF_SIMPLEPROGRESS;
        fAnyOperationsAborted:=false;
        hNameMappings:=nil;
      end;
      Result:=(ShFileOperation(SHFOS) = 0) and
               not SHFOS.fAnyOperationsAborted and FileExists(NewName)
    end
    else
      Result:=false
  end; {RenFile}
Hast du eine Idee...

Gruß Willie

Klaus01 28. Jan 2009 21:04

Re: RenFile
 
Guten Abend Willie,

nein, eine Idee habe ich nicht mehr.
Merkwürdig finde ich es, dass das Problem nur manchmal in Erscheinung tritt.
Ein bestimmtes Muster hast Du nicht feststellen können?
Warum, hast Du dann das RenFile in Verdacht?

Kannst Du das ganze auch auf Vista kompilieren (D6 sollte auch auf Vista laufen)?

Grüße
Klaus


Alle Zeitangaben in WEZ +1. Es ist jetzt 07:44 Uhr.

Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz