-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathPassword-Functions.psm1
108 lines (93 loc) · 3.36 KB
/
Password-Functions.psm1
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
Function New-Password
{
<#
.SYNOPSIS
Creates a password using a pretty random method. Good enough for most cases.
.DESCRIPTION
Creates a password using a pretty random method using the Windows Cryptographic Service Provider (CSP).
This is 'good enough' for most cases as without a hardware generator probably as good as Windows provides.
.PARAMETER Length
Length of passwords generated. Default is 16
.PARAMETER Count
Number of passwords to generate. Default is 1
.PARAMETER Strong
Generate passwords containing Upper, Lower, Numbers and complex Symbols. Not default
.PARAMETER Readable
Generate passwords containing Upper, Lower, Numbers and simple Symbols. Not default
.EXAMPLE
New-Password -Length 16
-Outputs one password using simple case, 16 charecters wide
New-Password -Length 20 -Count 20 -Readable
-Outputs twenty passwords, 20 charecters wide using readable format and symbols
.NOTES
This uses the Windows System.Security.Cryptography.RNGCryptoServiceProvider method which provides pretty good randomness.
#>
Param
(
[int]$Length = 16,
[int]$Count = 1,
[switch]$Strong,
[switch]$Readable
)
Begin
{
#Define strings uses for generation
$Alphas = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ"
$Numbers = "1234567890"
$Symbols = "*!@#$.-+"
$ExtendedSymbols = $Symbols + "%^&=()_{}|[]\:;<>?,/~"
if ($Strong -eq $true)
{
[string]$charSet = $Alphas + $Numbers + $ExtendedSymbols
}
elseif ($Readable -eq $true)
{
[string]$charSet = "abcdefghjkmnpqrstuvwxyzABCDEFGHJKLMNPQRSTUVWXYZ" + $Numbers + $Symbols
}
else
{
[string]$charSet = $Alphas + $Numbers + $Symbols
}
$Passwords = @()
}
Process
{
for ($Counter = 1;$Counter -le $Count; $Counter++)
{
$bytes = New-Object "System.Byte[]" $Length
$rnd = New-Object System.Security.Cryptography.RNGCryptoServiceProvider
$rnd.GetBytes($bytes)
$result = ""
# Get the first charecter as an alpha only. There are a lot of platforms and applications that only support this.
$i=0
$result += $Alphas[ $bytes[$i] % $Alphas.Length]
# Now use the specified set for the rest
for ( $i=1; $i -lt $Length; $i++)
{
$result += $charSet[ $bytes[$i] % $charSet.Length]
}
#Check for uniqueness
if ($result -cmatch "(?=.*\d)(?=.*[a-z])(?=.*[A-Z])(?=.*\W){1,$Length}" )
#Must have
#^0-9
#^a-z
#^A-Z
#^Symbol
#^No adjacency
{
#Set password to the result
$Passwords += $result
}
else {
#If it fails the match then run again by decrementing the counter
#Forcing randomness again....
$Counter--
}
}
}
End
{
#Output only
Return $Passwords
}
}