6

I've got 10 Linux servers that I need to lock down, by resetting the passwords for every single user all at once. The story behind this is long, but the general idea is that I need it to happen very quickly at a specific time. I'm going to use a single, tough password for all the user accounts (just initially), so this doesn't need to read from a password file or anything like that.

So what I need is the best way to script this out so I can reset all the passwords at once. I can extract a list of the user accounts with the cat /etc/passwd | cut -f1 -d: command, but that ends up including all of the accounts, including system accounts that I assume I shouldn't mess with.

So what's my best option here?

NOTE! When resetting passwords you also need to make sure to wipe anything extra from the ~/.ssh/authorized_keys file. Didn't remember this until after - thankfully I'd pretty much locked the servers down tightly and there was nothing in authorized_keys other than server-to-server stuff.

The How-To Geek
  • 245
  • 1
  • 3
  • 9

3 Answers3

5

You can select the UIDs >= 500 to make sure you only get real users and not system accounts and then use the option --stdin of passwd to change the passowrd.

Something like this should work:

 while IFS=: read u x nn rest; do  if [ $nn -ge 500 ]; then echo "YOURSTRONGPASSWORD" |passwd --stdin $u; fi  done < /etc/passwd
Daniel
  • 1,713
  • 1
  • 12
  • 16
  • I ended up using this just because it was so simple. You might note that you need two dashes before stdin, like --stdin. I'd edit your answer but I don't have enough rep on SF. – The How-To Geek Dec 13 '09 at 04:04
  • thanks, I updated the code. I wrote it correctly in the text and then I put a typo in the code... – Daniel Dec 13 '09 at 23:08
  • BTW: if you have NSF installed you'll want to make sure you didn't change the password for nfsnobody, that is a system account, but has uid=65k. If you did, you just need to set it back to locked with: passwd -l nfsnobody – Daniel Dec 13 '09 at 23:10
  • 2
    'passwd --stdin' is nonstandard; I'd suggest using 'usermod -p' instead. – MikeyB Dec 14 '09 at 04:30
  • @Daniel This does not work on Debian 9.0 – somethingSomething Aug 22 '18 at 04:17
  • Seems to `UID` must be `>= 1000`. According to [here](https://www.cyberciti.biz/faq/understanding-etcpasswd-file-format/): *UID 0 (zero) is reserved for root and UIDs 1-99 are reserved for other predefined accounts. Further UID **100-999** are reserved by system for administrative and system accounts/groups* – Mir-Ismaili Nov 14 '18 at 04:50
  • @MikeyB; But `usermod -p` expected a pre-encrypted one. It doesn't encrypt itself. not? See [here](https://askubuntu.com/a/136494/800487). – Mir-Ismaili Nov 14 '18 at 05:05
4

You can use something like the "newusers" command to update user passwords in batch mode. Create a file containing user:password combinations and load it via newusers... The password is entered unencrypted, but will be encrypted during the process.

newusers userpass.txt

userpass.txt would look like the /etc/passwd file. Same format.

I would copy /etc/passwd to a new file, delete the lines of system accounts and replace the second field, "x" with the generic password you wish to use, and then reimport using the newusers command.

ewwhite
  • 197,159
  • 92
  • 443
  • 809
  • This one is a great tool that I wasn't aware of, so while I went with the other method, thanks for introducing me to something new =) – The How-To Geek Dec 13 '09 at 04:29
2

Edit the shadow DB with:

vipw -s

which will lock the file against updates too, and then use your text-editor to replace the second field of every line which has a pw field.

Eg, use:

$ openssl rand -base64 12
gw9H5sqr8YioMdwd
$ openssl passwd -1
Password: 
Verifying - Password: 
$1$Nx/XBIYy$JGPhkX8DC9uJqggEFuKxP0

and then as root, use vipw -s; assuming that your text $EDITOR/$VISUAL is vi(m), then vipw will dump you into that and you might do:

:g/^[^:]*:[^*!:][^:]*:/s,:[^:]*,:$1$Nx/XBIYy$JGPhkX8DC9uJqggEFuKxP0:,

which is a basic pattern match, and on lines matching that pattern do a substitution (just once per line). The pattern match excludes lines with a password field of '!' or '*', so only sets passwords for users who already have passwords set, no matter what the uid is; this will protect you against cases where a packaging system created a "system" account with a high uid or whatever other nonsense some packager produced.

Note this will also reset the root password. If you want to exclude that, and root is on the first line, then replace the initial :g with :2,$g

Phil P
  • 3,080
  • 1
  • 16
  • 19