Domanda

Come posso recuperare l'attuale directory di lavoro di cmd.exe?

Questo sembra possibile. Ad esempio, utilizzando ProcessExplorer, selezionare CMD.exe, fare clic con il tasto destro, proprietà, scheda Immagine, " Directory corrente " riferisce la directory impostata usando i comandi CD o CHDIR.

Ho esaminato le classi .NET Process e ProcessStartInfo (ProcessStartInfo.WorkingDirectory restituisce sempre " ") e non riesco a trovare un modo per determinarlo. Nulla a PInvoke si distingue.

Ad esempio sto cercando di essere programmaticamente in grado di dire qualcosa come: Process.GetCurrentWorkingDirectory (processID) dove processID è un ID processo di Windows di un altro processo in esecuzione.

Esiste una soluzione, WinAPI o .NET?

[Aggiornamento]

Motivo per porre questa domanda:

Ho usato la barra di esplorazione del prompt dei comandi " per un po 'ed è fantastico tranne che se io " CD " in una nuova directory, anche la finestra corrente di Explorer non cambia. (ovvero la sincronizzazione è solo 1 via da Explorer al prompt dei comandi). Sto cercando di fare questo in 2 modi.

È stato utile?

Soluzione

Non testato, un possibile approccio:

Creare una DLL con un DllMain che utilizza GetThreadStartInformation () per trovare l'indirizzo del buffer, quindi utilizza GetCurrentDirectory per popolarlo. Questo dovrebbe essere OK, perché entrambe queste funzioni sono in kernel32, che è sempre presente. Dovrai avere una struttura lì per restituire successo / fallimento.

  1. Ottieni un handle per il processo cmd.exe.
  2. Allocare un po 'di memoria lì (VirtualAllocEx)
  3. Metti il ??percorso della tua DLL in memoria. (WriteProcessMemory)
  4. Carica la tua dll nello spazio degli indirizzi cmd.exe. (CreateRemoteThread con un punto di ingresso di LoadLibrary, l'argomento è la memoria allocata in precedenza.)
  5. WaitForSingleObject seguito da GetExitCodeThread (), fornisce l'HMODULE della DLL nel processo cmd.exe.
  6. ReadProcessMemory per ottenere la directory corrente.
  7. Scarica la tua dll dallo spazio degli indirizzi cmd.exe. Crea thread di discussione con un punto di ingresso di FreeLibrary, l'argomento è HMODULE.
  8. WaitForSingleObject in attesa dello scaricamento della DLL.

Bozzetto ampio: dettagli lasciati come un esercizio! Rischi: alloca la memoria nello spazio degli indirizzi cmd.exe, cambia il suo stato. Bisogna fare attenzione con le funzioni chiamate in DllMain.

Altri suggerimenti

Intendi la variabile% CD% in un file batch?

In questo modo:

set OLDDIR=%CD%
.. do stuff ..
chdir /d %OLDDIR% &rem restore current directory

Prova echo% CD% nel prompt dei comandi. :)

Bene, questo è ciò di cui hai bisogno, ecco una funzione PowerShell per farlo:

$(get-location)

Spero che questo aiuti.

Ho trovato tutto da qui .

Forse questa voce del forum sul forum Sysinternals contiene un suggerimento per soluzione. Cerca questo nella funzione GetProcessStrings:

// Get Command Line Block

// At offset 0x00020498 is the process current directory followed by

// the system PATH. After that is the process full command line, followed

// by the exe name and the windows station it's running on.

Questo articolo di CodeProject " Leggi le stringhe di ambiente del processo remoto " potrebbe anche essere utile.

  

AGGIORNAMENTO: questa non è non la soluzione, vedi i commenti a questa risposta: " Come diceva Janm   .Modules [0] .FileName (o   MainModuile.FileName) dà il   posizione dell'eseguibile in esecuzione   quel processo. Sto cercando di trovare il   directory di lavoro corrente (che può essere   modificato utilizzando il CD o CHDIR   comandi) ".

Puoi utilizzare Spazio dei nomi System.Diagnostics . Ecco un esempio come applicazione console C #. Dal nome file è possibile estrarre facilmente le informazioni sul percorso (System.IO.Path ...).

Assicurati di avere le autorizzazioni (esegui come amministratore) per farlo.

Spero che questo aiuti. Ecco il codice di lavoro (testato):

using System;
using System.Diagnostics;
using System.IO;

namespace Test
{
    class Program
    {
        static void Main(string[] args)
        {
            Process[] procList =  Process.GetProcessesByName("cmd");

            string sFileName;

            for (int i = 0; i < procList.Length; i++ )
            {
                Console.Write(procList[i].Id);
                Console.Write(" ");

                try
                {
                    sFileName = procList[i].Modules[0].FileName;
                    Console.Write("(");
                    Console.Write(Path.GetFileName(sFileName));
                    Console.Write("): ");
                    Console.WriteLine(Path.GetDirectoryName(sFileName));
                }
                catch (Exception ex)
                {
                    // catch "Access denied" etc.
                    Console.WriteLine(ex.Message);
                }


            }

        }
    }
}

Qui il output sul mio computer (ho aperto quattro righe di comando):

alt text http://img236.imageshack.us/img236/3547/processworkingdirvn4 .png

Prova questa semplice proprietà di ambiente:

Environment.CurrentDirectory ()

Vedi la mia risposta a una domanda simile (da solo). Ho scritto un'utilità da riga di comando e un wrapper C # per leggere le variabili di ambiente di processo. Per la mia domanda (ottenere la directory corrente per Java), ho semplicemente letto la directory catalina_base.

Non sono sicuro che ciò si applichi direttamente a cmd.exe. L'utilità fornita nell'articolo Code Project non ha funzionato con cmd.exe.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top