Delle volte, per specifice esigenze progettuali, potrebbe essere necessario eseguire codice all’interno di un applicazione utilizzando credenziali di accesso diverse da quelle con cui l’utente è attualmente connesso, un esempio pratico può essere l’utilizzo di oggetti COM che si interfacciano direttamente con il sistema all’interno di un applicazione web, se il contesto prevede che l’utente esecutore dell’applicazione web è il nostro amato ASPNET potremmo incorrere in alcuni problemi relativi ai privilegi che questo account possiede sulla macchina server. Per risolvere il problema si possono seguire due strade:
Configurazione del file web.config
Modifichiamo il file web.config impostando proprietà specifiche per ogni pagina, in questo caso (nell’esempio riportato sotto), abbiamo impostato un comportamento diverso per la pagina demo.aspx, cioè, nel momento in cui viene eseguita questa pagina, l’utente esecutore non sarà più ASPNET ma quello impostato nella proprietà identity.
Questa operazione, secondo me, risulta molto pericolosa, pensare di elevare i privilegi di esecuzione all’interno di una pagina per eseguire una porzione di codice che richiede un diverso tipo di account è eccessivo e poi espone l’applicazione a dei rischi molto elevati!
Esecuzione mirata di codice con privilegi elevat.
In ambiente DOT.NET abbiamo la possibilità di poter richiamare librerie esterne, del sistema operativo, ed utilizzarle internamente ai nostri progetti per gli scopi più disparati. Tra le tante cose possiamo richiamare una libreria che ci permette di eseguire il “Login” sul sistema operativo, con privilegi diversi da quelli attualmente in uso. Possiamo creare un nostro oggetto, che in questo caso chiameremo LogonService che implementa i metodi necessari ad eseguire questa operazione.
public const int LOGON32_LOGON_INTERACTIVE = 2;
public const int LOGON32_LOGON_SERVICE = 3;
public const int LOGON32_PROVIDER_DEFAULT = 0;
[DllImport("advapi32.dll", CharSet = CharSet.Auto)]
public static extern bool LogonUser(
String lpszUserName,
String lpszDomain,
String lpszPassword,
int dwLogonType,
int dwLogonProvider,
ref IntPtr phToken
);
[DllImport("kernel32.dll", CharSet = CharSet.Auto)]
public extern static bool CloseHandle(IntPtr handle);
In questo modo abbiamo implementato la funzione LogonUser che non fà altro che richiamare le API di windows necessarie per eseguire l’autenticazione di windows e nel caso in cui vada a buon fine restituisce un Token necessario per poter gestire questo nuovo utente loggato. Ora veniamo al sodo, come eseguire una particolare porzione di codice con privilegi pari a quelli dell’utente loggato; all’interno della stessa classe in cui abbiamo inserito il codice per l’utilizzo del metodo statico LogonUser() scriviamo:
private IntPtr userToken;
public bool Impersonate(string username, string password, string domain)
{
bool logged = LogonUser(username, domain, password, LOGON32_LOGON_INTERACTIVE, LOGON32_PROVIDER_DEFAULT, ref userToken);
if(logged)
{
// I parametri sono corretti ed è stato possibile effettuare il login
WindowsIdentity identity = new WindowsIdentity(userToken);
WindowsImpersonationContext = identity.Impersonate();
}
return logged;
}
Istanziamo
using(LogonService ls = new LogonService())
{
if(ls.Impersonate("utente","password","dominio o stringa vuota"))
{
// Tutto il codice presente in queste parentesi verrà eseguito con privilegi pari a quelli dell'utente loggato.
}
}
L’esempio fornito serve per dare informazioni utili sul meccanismo di funzionamento di questo oggetto, ho pensato di pubblicarne una versione più completa, spero possa essere utile a qualcuno!
0 Responses to “C# – Effettuare il logon con username e password tramite codice”