How to Get and Change Windows Credential Username and Password - c#

I want to write a application in C# using WMI that can get and change Windows credential stored in the Windows Credential Manager, as you see in the picture below:

Ookii.Dialogs contains a credential dialog, which calls into CredUIPromptForCredentials or CredUIPromptForWindowsCredentials as appropriate.
Edit: The Credentials API is detailed at http://msdn.microsoft.com/en-us/library/aa374731%28v=VS.85%29.aspx#credentials_management_ui_functions - but it could be tricky to implement from managed code. After CredUIPromptForWindowsCredentials you would call CredWrite to save the credentials.

Edit: Misunderstood the original question since the pic wasn't visible.
I'm not sure if you can do what you want via WMI. However, I think it might be possible using the DPAPI, but the documentation for that doesn't seem to make it very easy. However, there is an opensource project called NCrypto that has a class called UICredentialsHelper which might show you how to do it, or at least how to get started.

There is no Windows API to get a user's password. Passwords are not stored in Windows. Instead Windows stores a one-way hashed version.
You can get the username using WindowsIdentity.GetCurrent(). Alternatively you can get the logged in user name via the Environment.UserName property.
Although to change credentials..... good luck :) Thats my best answer on that. I don't think Microsoft would ever give us the ability to do that.

[void]Windows.Security.Credentials.PasswordVault,Windows.Security.Credentials,ContentType=WindowsRuntime]
(new-object Windows.Security.Credentials.PasswordVault).RetrieveAll() | % { $.RetrievePassword(); $ }

Related

How can I get an X509Certificate2 object for an authenticated user?

I'm a bit out of my depth here so bear with me if I say/ask/do something idiotic.
Anyways, I have a dll that I need to use for a project of mine. Essentially, this dll is my interface to another service I need to use. I don't own the dll so I can't change it's interface/code at all, and the interface to the underlying service is unknown (expect by using its SDK dll obviously). One of the functions I need to use from this sdk requires me to provide either the user's name & password in plain String format, in String and SecureString formats, or just provide an X509Certificate2 object.
My website is currently configured to use windows authentication. What I would like to do is be able to call into this dll without asking for the user's password (seeing as they already had to enter it in order to access the site). I am assuming that there is a snowball's chance in hell that I have access to the user's password itself as either a String or SecureString, but it looked like I could construct the x509 certificate object doing something like this:
var x509 = new X509Certificate2(Request.ClientCertificate.Certificate);
Unfortunately, it appears like Request.ClientCertificate.Certificate is always empty for whatever reason.
Is there some other way that I can access this information? If I have sufficient information to impersonate the user (via HttpContext.Request.LogonUserIdentity.Impersonate()), then should I not have enough information to construct a X509Certificate2 object for this user as well? If not, what would I need to do to get the client certificate populated in the request?
Any help is greatly appreciated. Thanks!

Hide password in c# source code

I am using the following code in c# to download a file from my website:
WebClient webClient = new WebClient();
webClient.Credentials = new System.Net.NetworkCredential("username", "password");
webClient.DownloadFile("http://example.com/file.txt", "file.txt");
The file is only downloaded when certain criteria are met, so I don't want the users to be able to access the files on my site
My corcern is that if a curios users decompiles the code, he will find the password and be able to access all the files on my site.
I've read that a secure way to save the password is to store its hash, but I don't know how to implement it in this example.
What options do I have to keep my password secure and make it impossible for a user to find it?
A sobering reality: You can't protect information contained in your program like this.
A must-do: Choose a username/password that is only for accessing the special files this single program needs - not your "access my whole website" username and password.
But just know that all you are doing is adding a little bit of an obstacle, here; anyone who wants to can examine your program and find the username and password.
The only 'correct' way to do this is to do it based on the user's own credentials; their username and password within your own system, for example. Then you would need to give them access based on that information, and your program would need to prompt them for it.
You simply don't. Users give you passwords to do stuff, not the other way around.
If the user has to prove "certain conditions", then pass proof of those certain conditions to the server, and let it decide whether to allow the download or not.
There is no way to prevent that. If you program is able to access the file under condition X, the user is able to trick the program into condition X and get the file no matter what. You can make it harder, but you can't make it impossible.
If the data are in the program itself you can considered them as already being exposed to users. If the credentials are on the users computer regardless on how many measures you take to combat this there is always a possibility to find a way around it.
What you can do is implement a login form for your program and provide the users with login info. Then when the user enters the login info do a check on the server side if the credentials exist (usually by checking in a database) and if it matches send them the file.
But as always, there is the issue with users just sharing the login info with other people and so on.

Forgot Password

I am trying to create a web application to reset the password based on question/answer using System.Web.Security API.
I get an exception:
DirectoryServicesCOMException (0x8007202f): A constraint violation
occurred" if user provide one bad answer to the question.
If I reset value of attributeMapFailedPasswordAnswerCount to not set the account becomes active again.
Account Lockout threshold in AD is set to 20 logon attempts.
I am novice on AD knowledge and will be grateful if someone can guide me how to solve this problem.
Thank you.
I'm guessing you're using ASP.NET? I don't really have any experience with it, nor do I have much experience with .NET in general (I'm still learning myself), but this was a really useful link providing examples of various Active Directory API's (link). Including resetting a user password. Here is a link to the DirectoryEntry class, if you aren't sure how to set it up (link). Plus, just browsing through the namespace documentation is very, very helpful (link). Probably the only thing I like about Microsoft is their good documentation.
I usually do something like this (in IronPython, so it will not translate directly to code you can use):
ou = System.DirectoryServices.DirectoryEntry("LDAP://ou=Users,dc=whatever,dc=something,dc=localetc")
search = System.DirectoryServices.DirectorySearcher(ou, "(samAccountName="+acc"+")", Array[str](["distinguishedName"]]))
result = search.FindAll() # note 1
if result.Count != 1:
raise BadError
else:
ent = System.DirectoryServices.DirectoryEntry(result[0].Properties["distinguishedName"][0])
ent.Username = admin # note 2
ent.Password = pwd
ent.Invoke("SetPassword", Array[object](["newpassword!"]))
ent.Properties["LockOutTime"].Value = 0
ent.CommitChanges()
Notes:
If this ever returns more than one result, you have issues.
this and the password are only necessary if the account running this does not have permission to change the user. I run these on an unprivelaged account so I have to include my admin credentials in the script (don't worry, they aren't hardcoded)
Oh and you're account lockout threshold is quite high. I would suggest 3-5, depending on the aptitude of your users.

C# SMF Authentication (Licensing)

I'd like to use C# to authenticate a username and password through SMF (Simple Machines Forum). I was wondering if there is a secure way to send a username and password string through HTTPWebRequest that can be easily combined with SMF's authentication system, unless there is a better way (I do not want to use direct mySQL access).
What I am thinking of is something like, on the server side, check if the login is successful. If so, it will echo a certain string "true" and "false".
I've taken a look at the "verification hooks", but I'm not sure how to use them. I also took a look at the login scripts and saw that there's quite a bit of security behind it. Does SMF have any sort of API that can isolate just the login authentication and return a true/false?
Thanks.
There's a quasi RESTful API for SMF 2.x here:
http://www.simplemachines.org/community/index.php?topic=458832.0
One of the functions will validate your login for you. If you need to expand it to do other things it can easily be done.

System.Security.Principal.WindowsIdentity and WinForms Authentication

I'd like to utilize the Windows Authentication Model for authenticating users that use my C# 3.5 WinForms application:
The user that has logged on Windows is automatically logged in to my application.
If the user wants to log in explicitely, his user name and password should be checked by Windows, or even better, prompted by Windows with a standard Windows Dialog. The outcome should be another WindowsIdentity object.
The first was very easy to solve long time ago: I read the
WindowsIdentity identity = WindowsIdentity.GetCurrent();
Just to make sure, I check for the
if (identity.IsAuthenticated) { ... }
For the second case I've found some API calls in other SO Q&A's, but I'm pretty sure there must be a managed way for that, am I wrong?
Further I wonder whether my approach for 1. is save and appropriate. Thanks for your feedback!
Update: According to Ivan, I have to use the P/Invoke approach. This is basically alright, but then I still need a way to retrieve a WindowsIdentity object for that certain user, which has its IsAuthenticated property set to true. The P/Invoke call in itself doesn't return such an object. How can this be done?
I am not certain about this but it looks like you want to use the WindowsIdentity Ctor that takes an IntPtr. To get the parameter that is passed into this constructor you can PInvoke the Win32 API LogonUser() function. This will give you a WindowsIdentity for this user.
There is no managed way of doing this, you have to do pinvoke (api call) as you said. Approach #1 is totaly ok ... trust microsoft :)

Categories