Solutions for Keeping Passwords Fresh
April 24, 2015
Our management wants our 3000 users to be forced to change their password on a regular basis. Also, certain rules must be applied to the new password. We don’t have VEsoft’s Security/3000, although we do have MPEX. I therefore have two options. 1. Write something myself, or 2. See if there is anything in the Contributed Software Library that will do the job, or can be modified to supply the required solution.
Homegrown and bundled solutions follow. Jeff Vance offered this:
There is a pseudo random password generator available among the Jazz files which knows MPE’s password rules. See RANDNAME. There are also UDCs which force a password to be supplied when using NEWUSER, NEWACCT and NEWGROUP CI commands. These required passwords can be random or user entered with a minimal length enforced.
Then he added as an afterthought, a strategy to program your own password system:
I haven’t thought about it much, but it seems you could have a password file (maybe a CIRcular file?) for each user on the system. This file would have their last N passwords, and the modified date of the file would be the date their password was most recently changed.
A logon UDC could detect if the password file for that user exists. If not create it and require a new password right then. If the password file exists then get it’s modified date and compare that to today’s date. If greater than X days then in a loop prompt for a new password. Validate the entered password against previous N passwords and your other rules. Maybe run a dictionary checking program to make sure the password is not common, etc.
Update the user-specific password file with their new password, and then logon the user.
The solution that your management demands is going to cost more for you to develop, implement, or maintain than it’ll take for you to get Security/3000. If you have no choice other than to develop a product, then I’d certainly model it after what VEsoft has already done. That is:
Based on a system-wide UDC, examine all sessions (it is just sessions, yes? By the way, a DSLOGON from inside a job is still a session.) against a ‘database’ (By the way, just how secure is this database? A real database needs passwords... Who’s going to maintain that? A flat file could be lock-worded, but that’s not a slam-dunk answer.) a database which is looking for the ‘age’ of the password (By the way, are you going to provide an advance warning period?).
If it is time to change the password, get the ‘new’ password from the user... but writing the rules is a pain, and keeping track of reused passwords is just annoying. Auditors in the states love when you can say the password is one-way encrypted. Dunno what your management is saying for encrypting an MPE password.
Then came a solution rolled up by Paul Christidis
Some years ago I had developed a set of command files that could be used to require users to have passwords. Later on, mostly as an exercise, I enhanced the process to age passwords and to automatically assign ‘random’ passwords as they expire. The random passwords are comprised of alternating consonants and vowels, they can have a minimum and maximum length and optionally a random digit can be inserted.
The entire ‘process’ is comprised of a system batch job (should be running always), a command file that is invoked by a log-on UDC and communicates with the batch job, a ‘control’ command file that starts and stops the batch job, a command file to determine the password age and a command file to generate the random password. Below are the comments from the batch job. They explain some of the details.
!# Author: Paul H. Christidis
!# Remarks: This job 'listens' at a message file for any requests to
!# determine if a user has a password. Once that determination is
!# made it passes back to the session an indicator to that effect.
!# A command of STOP causes the job to terminate.
!#
!# The request comes via the execution of a command file or a System
!# wide UDC and it is comprised by the file name where the reply should
!# be placed and the user's name and account.
!# This job does NOT return the user's password, it only writes in
the
!# message file specified by the client the command:
!# setvar user_password true/false
!# The client then executes the command and tests the setting of the
!# variable 'user_password' to decide what action to take.
!#
!# DATE: 06/08/2004 *** WHILE RETAINING THE ABOVE BEHAVIOR ***
!# The job logic was changed to assign a new password after 30 days. A
!# file in the posix space is built using the user's name. Then at each
!# logon a command file is used to determine the file's age, using its
modify
!# date, and when it is older than 30 days another command file is used to
!# generate a random password. Said password is sent back to the session
!# and the user is informed about his new password.
!#
!# If the 'job/session' name is not to be used in creating the posix
file
!# that will be used to age the password, then the value of the CI
variable
!# 'pw_UseSess' should be set to 'FALSE'.
!#
!# DATE: 06/10/2004 [Added alternative aging values functionality]
!# Alternative aging limits are kept in an ASCII file "pswrdage"
comprised
!# of 'setvar' commands, for each MPE account, MPE user or Session name.
It
!# should adhere to the following format:
!# SETVAR SYS_MANAGER_XTIDIS_pwage 45
!# SETVAR SYS_MANAGER_pwage 40
!# SETVAR SYS_pwage 35
!#
!# The above have the following implications:
!# The user's "xtidis,manager.sys" password expires in 45 days
!# The user's "manager.sys" password expires in 40 days
!# Any other user of the "sys" account has their password expire in 35
days
!# While the 'default' 30 days applies to every other user on the
system.
!#
!# NOTE 1: Suffix of '_pwage' is required.
!# NOTE 2: A negative or zero setting equals to NO password aging.
!# NOTE 3: The order MUST be 'ActName_UserName_JobName_pwage'.
!#
!# Date: 06/11/2004 [Added code to 'force' a password change]
!# When the CI variable "ForcePwChange" is set to TRUE in the session
that
!# executes the command file, the 'passed' code is changed and the batch
job
!# forces the password change (Unless it was already changed on the same
day)
!# <---------------------------------------------------->
Dave Powell coded up some of the fine print nicely in his contribution:
It ought to be possible to do everything for free, using just MPE. Editing the new password is the ugly part, but if you randomly assign it that issue goes away. The next issue is that the :password command seems to like to be purely interactive, as in:
echo oldpass >> tempf
echo newpass >> tempf
echo newpass >> tempf
:password < tempf
password
Command not allowed in noninteractive environment. (CIERR 2500)
PASSWORD WAS NOT CHANGED.That leaves the altuser cmd, which needs AM cap. If you don't want a background job (like Paul's suggestion), you can have the command file (called by your logon UDC) use the echo command to build job with AM cap, which it then streams, kind of like (untested, but I have working examples of cmd-files building other jobs):
ECHO !!JOB ACCTMGR/PASS.SOMEACCT; HIPRI >> TF
ECHO !!ALTUSER !HPUSER;PASS=!NEW_PASS >> TF
ECHO !!SETVAR STREAMED_BY WORD(HPSTREAMEDBY,"()",2) >> TF
ECHO !!TELL !!STREAMED_BY Your new password is !NEW_PASS >> TF
ECHO !!EOJ >> TF
STREAM TF
ECHO Please note your new password when it appears
PAUSE 99; JOB = !HPLASTJOB
PURGE TF, TEMP
If I haven't screwed up the fine print too badly, this code in the middle of the password cmd-file runs the job that changes your password, then waits for the job to tell you what the new password is. The single exclamations before HPUSER & NEW_PASS mean that values that are variables to the session and command-file become hard-wired values for the job.
Before all this your cmd-file checks the date, gets a random password, etc., as posted by others. After it the cmd-file writes (or just builds) a file that serves as a timestamp. But I am not too comfy with putting the passwords into a plain-text file, so I might skip that part (remember, the user needs both read and write access to it). Put the command file in a group that users have xeq access to, but not read/write access.