Public/New-SecurityScan.ps1
<#
.SYNOPSIS This function will scan the files in the OneDrive folder for any security issues. .DESCRIPTION This function will scan the files in the OneDrive folder for any security issues. .PARAMETER pathOfOneDrive The path of the OneDrive folder. This is a relative path to the user's OneDrive folder, don't provide the full path here. .PARAMETER accessToken The access token to access the OneDrive folder. This is optional, if not provided, the function will prompt for the access token. .OUTPUTS This function will generate a report of the security issues found in the OneDrive folder, and can be export to csv. .LINK https://github.com/code365opensource/microsoft.security.toolkit #> function New-SecurityScan { [cmdletbinding()] [Alias("amisecure")] param ( [Parameter(Mandatory = $true)] [string]$pathOfOneDrive, [string]$accessToken ) # connect to Microsoft Graph, if the accessToken is not provided, prompt for the access token, otherwise use the provided access token (parse it to secure string) if (-not $accessToken) { Connect-Graph -Scopes "Files.Read", "Files.Read.All", "InformationProtectionPolicy.Read" -NoWelcome } else { Connect-Graph -AccessToken (ConvertTo-SecureString $accessToken -AsPlainText -Force) -NoWelcome } # initialize the result $file_info = @{} $file_info_sensi = @{} $file_info_access = @{} $file_info_permission = @{} $file_info_scope = @{} $file_info_shared = @{} $file_info_access_90days = @{} try { # Get all files in the specified folder from OneDrive $graph_url_getItems = "https://graph.microsoft.com/v1.0/me/drive/root:/${pathOfOneDrive}:/children?select=name,id" $response = Invoke-MgRestMethod -Uri $graph_url_getItems -Method GET -ErrorAction Stop # Check if the response contains any files if ($response.value -and $response.value.Count -gt 0) { $data = $response.value foreach ($file in $data) { # Store file id and name in the dictionary $file_info[$file.id] = $file.name } } else { Write-Host "No files found in the specified folder." Exit 1 } } catch { Write-Host "An error occurred while retrieving files: $_" Exit 1 } # get the required information for each file $graph_baseUrl = 'https://graph.microsoft.com/v1.0/me/drive/items' $id_to_display_name = Get-SensitivityLabelsMapping foreach ($key in $file_info.Keys) { # get sensitivity label try{ $url_sen = "$graph_baseUrl/$key/extractSensitivityLabels" $response = Invoke-MgRestMethod -Uri $url_sen -Method POST -ErrorAction Stop $data = $response.labels $id = $data[0].sensitivityLabelId if ($data -and $data[0].sensitivityLabelId) { $id = $data[0].sensitivityLabelId $file_info_sensi[$file_info[$key]] = if ($id_to_display_name.ContainsKey($id)) { $id_to_display_name[$id] } else { "General" } } else { $file_info_sensi[$file_info[$key]] = "General" } } catch { Write-Host "An error occurred while retrieving sensitivity label: $_" $file_info_sensi[$file_info[$key]] = "General" } try { $url_access = "$graph_baseUrl/$key/analytics/alltime?select=access" $response = Invoke-MgRestMethod -Uri $url_access -Method GET -ErrorAction Stop $accessLog = $response.access if ($null -ne $accessLog) { $file_info_access[$file_info[$key]] = $accessLog } else { $file_info_access[$file_info[$key]] = $null } } catch { Write-Host "An error occurred while retrieving access data: $_" $file_info_access[$file_info[$key]] = $null } # get recent 90 days analytics log try { $startDate = (Get-Date).AddDays(-90).ToString('yyyy-MM-dd') $url_access = "$graph_baseUrl/$key/getActivitiesByInterval(startDateTime='$startDate',endDateTime='',interval='month')?select=access" $response = Invoke-MgRestMethod -Uri $url_access -Method GET -ErrorAction Stop $accessLog = $response.value if ($null -ne $accessLog) { $file_info_access_90days[$file_info[$key]] = $accessLog } else { $file_info_access_90days[$file_info[$key]] = $null } } catch { Write-Host "An error occurred while retrieving access data: $_" $file_info_access_90days[$file_info[$key]] = $null } # get permissions try { $url_userNum = "$graph_baseUrl/$key/permissions?count=true&top=0" $response_userNum = Invoke-MgRestMethod -Uri $url_userNum -Method GET -ErrorAction Stop $userNum = $response_userNum['@odata.count'] $url_linkNum = "$graph_baseUrl/$key/permissions?filter=link/scope eq 'organization' or link/scope eq 'anonymous'&count=true&top=0" $response_linkNum = Invoke-MgRestMethod -Uri $url_linkNum -Method GET -ErrorAction Stop $linkNum = $response_linkNum['@odata.count'] $url_owner = "$graph_baseUrl/$key/permissions?filter=roles/any(property:property eq 'owner')&select=grantedToV2,roles" $response_owner = Invoke-MgRestMethod -Uri $url_owner -Method GET -ErrorAction Stop if ($response_owner.value -and $response_owner.value[0] -and $response_owner.value[0].grantedToV2.user.email) { $owner = $response_owner.value[0].grantedToV2.user.email } else { $owner = $null } $file_info_permission[$file_info[$key]] = $userNum $file_info_scope[$file_info[$key]] = $linkNum } catch { Write-Host "An error occurred while retrieving permission data: $_" $file_info_permission[$file_info[$key]] = -1 $file_info_scope[$file_info[$key]] = -1 $owner = $null } # get activities log try { $url_activities = "$graph_baseUrl/$key/activities?select=action,actor" $response = Invoke-MgRestMethod -Uri $url_activities -Method GET -ErrorAction Stop $shared = $false foreach ($item in $response.value) { Get-Activity -entry $item -owner $owner -shared ([ref]$shared) if ($shared) { break } } $file_info_shared[$file_info[$key]] = $shared } catch { Write-Host "An error occurred while retrieving activity data: $_" $file_info_shared[$file_info[$key]] = $null } } $timestamp = (Get-Date).ToString("yyyy-MM-dd_HH-mm-ss") $csvFileName = "scan_report_$timestamp.csv" $csvFilePath = Join-Path -Path $PSScriptRoot -ChildPath $csvFileName $csvData = @() # generate report for each file foreach ($key in $file_info.Keys) { $fileName = $file_info[$key] $sensitivity = $file_info_sensi[$fileName] Write-Host $fileName $sensitivity $accessLog = $file_info_access[$fileName] $accessLog90days = $file_info_access_90days[$fileName] $permissionCount = $file_info_permission[$fileName] $scope = $file_info_scope[$fileName] $sharedWithOthers = $file_info_shared[$fileName] # Check if the file is private, and no access logs belongs to others. $passPrivateAndNoAccessTest = Test-PrivateAndOthersNoAccess -permissionCount $permissionCount -accessLog $accessLog # Check if the file has been shared by others, rather than by the owner. $passSharedByOthersTest = Test-SharedByOthers -sharedWithOthers $sharedWithOthers # Check if the file is classified as 'confidential' or 'high confidential', but shared with 'organization' or 'anonymous'. $passConfidentialAndNoOrgScopeTest = Test-ConfidentialAndNoOrgScope -scope $scope -sensitivity $sensitivity # Check if the file has not been used in the last 90 days, but still has permission settings. $passUnusedWithPermissionsTest = Test-UnusedWithPermissions -accessLog90days $accessLog90days -permissionCount $permissionCount # Generate report based on check results $csvData += New-Report -fileName $fileName ` -passPrivateAndNoAccessTest $passPrivateAndNoAccessTest ` -passSharedByOthersTest $passSharedByOthersTest ` -passConfidentialAndNoOrgScopeTest $passConfidentialAndNoOrgScopeTest ` -passUnusedWithPermissionsTest $passUnusedWithPermissionsTest } $csvData | Export-Csv -Path $csvFilePath -NoTypeInformation Write-Host "Scan report saved to: $csvFilePath" $result } # SIG # Begin signature block # MIIdKgYJKoZIhvcNAQcCoIIdGzCCHRcCAQExDzANBglghkgBZQMEAgEFADB5Bgor # BgEEAYI3AgEEoGswaTA0BgorBgEEAYI3AgEeMCYCAwEAAAQQH8w7YFlLCE63JNLG # KX7zUQIBAAIBAAIBAAIBAAIBADAxMA0GCWCGSAFlAwQCAQUABCCDpXpHnQ86TwC/ # saxB/hiv5UXkynhjwEIjdOis7jTsNKCCA0YwggNCMIICKqADAgECAhAdkYHz+qFO # vkQjYqzHr3pKMA0GCSqGSIb3DQEBCwUAMDkxNzA1BgNVBAMMLkNvZGVTaWduaW5n # IENlcnRpZmljYXRlIGZvciBQb3dlclNoZWxsIE1vZHVsZXMwHhcNMjQwNjEyMDUw # ODAyWhcNMjUwNjEyMDUyODAyWjA5MTcwNQYDVQQDDC5Db2RlU2lnbmluZyBDZXJ0 # aWZpY2F0ZSBmb3IgUG93ZXJTaGVsbCBNb2R1bGVzMIIBIjANBgkqhkiG9w0BAQEF # AAOCAQ8AMIIBCgKCAQEAwdSzTBb7ni0tRubblITxoGHzXlvwu8Y5ndoElOvIKaey # AFW8+tYCPG5zATsoGGE3f8g6Wtv8JgEjH45ZOhRBjghEVpw/9Iszal5SmucjUlqB # fMvts+M/x9G7h6GGAQFy65xgQqyCVJA10x2NDheb7cBRCRRZVkT+CUv1dbS41bsO # BMKDUTumbU7vHk2FSJ5H6f31cj238qboI4g2GD2gIsWID+GhAfzxrmXMV6VgMKqW # GNlK5g/X2tSM6Aygnx1itXrrV3LwDOYiAAs+j87jEsYhxe3CnFgtDsi4UtW/lFem # eEiOh9Vd6LaTxNoleV/PGz3FU7t6nnZmIOsjOFWLHQIDAQABo0YwRDAOBgNVHQ8B # Af8EBAMCB4AwEwYDVR0lBAwwCgYIKwYBBQUHAwMwHQYDVR0OBBYEFMTYcpJNvUO8 # TYpuvvHtzPkUUUmkMA0GCSqGSIb3DQEBCwUAA4IBAQAihkTQ6zo1SNboEZ2C5yXr # Hf5FoMRFBij0o0drMYEwDbiVCNGXkk74nNqXnGm+CJ0jkPHkM35uC/JGGGyToyBF # uC27hC6+WsTMlVlJZKr7N5WLaM97hwf5xtEWg1c1s0vLKx92AKSGgqJRU7rlRMaX # 5oOROmFwLqMj15Oon73EhZNqpjfRsKgMxJJw03n6KwMNvzNTXlsiaS0mvAnFzKFp # msuvtWJfp8fxHvEQckJzFr2EldNKKyTTZjbN5JfbQWZGIuxftYXZ0JKwXleZhNxZ # MtkuHzjcpCoBgdIYI3FidWcZgUltoSLRZzM/iVLX6MAX2mjHQOBNWG/gOeZk28qo # MYIZOjCCGTYCAQEwTTA5MTcwNQYDVQQDDC5Db2RlU2lnbmluZyBDZXJ0aWZpY2F0 # ZSBmb3IgUG93ZXJTaGVsbCBNb2R1bGVzAhAdkYHz+qFOvkQjYqzHr3pKMA0GCWCG # SAFlAwQCAQUAoHwwEAYKKwYBBAGCNwIBDDECMAAwGQYJKoZIhvcNAQkDMQwGCisG # AQQBgjcCAQQwHAYKKwYBBAGCNwIBCzEOMAwGCisGAQQBgjcCARUwLwYJKoZIhvcN # AQkEMSIEIKEBPICYZLPFrWYrq4tcbEmFcBbPz0m9pGveHq12BIOAMA0GCSqGSIb3 # DQEBAQUABIIBAEZsniuVOKNtF6HSn/d7LHtenjpYpz0w6mjTBL+3fdsRxzK41F4N # H++RczyPNsorJIpzEv8cj/HcPzoZ9CtLIus0RuxLXWgApRfNHq0okybmFCoq/HHy # m9/mgNgCD6s6l6k9udYx5at89i08+nTAqOlQM2NFHTcisM08eQi6TFVUBoaEKEDI # qSgWEeJoJ49If4utw6M3MIHvoqzahaYDfluNPC4QoWGF1wbcveVzMh9Pds9035Tl # eJx0CyZ5HU1IT4NWRx0jXMZ4BlkFP8FhxwMsWABLbRfMYSpTdZK7ulZH2l799rXI # FcRNASRvbxACpEvhouLhbBukpDn7JV++bgihghdAMIIXPAYKKwYBBAGCNwMDATGC # FywwghcoBgkqhkiG9w0BBwKgghcZMIIXFQIBAzEPMA0GCWCGSAFlAwQCAQUAMHgG # CyqGSIb3DQEJEAEEoGkEZzBlAgEBBglghkgBhv1sBwEwMTANBglghkgBZQMEAgEF # AAQgchtypFijQmAru56XEeHoWeC6I5gkw/Y5s/A2coy7UvsCEQCfoJ2xrNT5lJpR # buyhrhrfGA8yMDI0MDkxNDA3Mzc1MlqgghMJMIIGwjCCBKqgAwIBAgIQBUSv85Sd # CDmmv9s/X+VhFjANBgkqhkiG9w0BAQsFADBjMQswCQYDVQQGEwJVUzEXMBUGA1UE # ChMORGlnaUNlcnQsIEluYy4xOzA5BgNVBAMTMkRpZ2lDZXJ0IFRydXN0ZWQgRzQg # UlNBNDA5NiBTSEEyNTYgVGltZVN0YW1waW5nIENBMB4XDTIzMDcxNDAwMDAwMFoX # DTM0MTAxMzIzNTk1OVowSDELMAkGA1UEBhMCVVMxFzAVBgNVBAoTDkRpZ2lDZXJ0 # LCBJbmMuMSAwHgYDVQQDExdEaWdpQ2VydCBUaW1lc3RhbXAgMjAyMzCCAiIwDQYJ # KoZIhvcNAQEBBQADggIPADCCAgoCggIBAKNTRYcdg45brD5UsyPgz5/X5dLnXaEO # CdwvSKOXejsqnGfcYhVYwamTEafNqrJq3RApih5iY2nTWJw1cb86l+uUUI8cIOrH # mjsvlmbjaedp/lvD1isgHMGXlLSlUIHyz8sHpjBoyoNC2vx/CSSUpIIa2mq62DvK # Xd4ZGIX7ReoNYWyd/nFexAaaPPDFLnkPG2ZS48jWPl/aQ9OE9dDH9kgtXkV1lnX+ # 3RChG4PBuOZSlbVH13gpOWvgeFmX40QrStWVzu8IF+qCZE3/I+PKhu60pCFkcOvV # 5aDaY7Mu6QXuqvYk9R28mxyyt1/f8O52fTGZZUdVnUokL6wrl76f5P17cz4y7lI0 # +9S769SgLDSb495uZBkHNwGRDxy1Uc2qTGaDiGhiu7xBG3gZbeTZD+BYQfvYsSzh # Ua+0rRUGFOpiCBPTaR58ZE2dD9/O0V6MqqtQFcmzyrzXxDtoRKOlO0L9c33u3Qr/ # eTQQfqZcClhMAD6FaXXHg2TWdc2PEnZWpST618RrIbroHzSYLzrqawGw9/sqhux7 # UjipmAmhcbJsca8+uG+W1eEQE/5hRwqM/vC2x9XH3mwk8L9CgsqgcT2ckpMEtGlw # Jw1Pt7U20clfCKRwo+wK8REuZODLIivK8SgTIUlRfgZm0zu++uuRONhRB8qUt+JQ # ofM604qDy0B7AgMBAAGjggGLMIIBhzAOBgNVHQ8BAf8EBAMCB4AwDAYDVR0TAQH/ # BAIwADAWBgNVHSUBAf8EDDAKBggrBgEFBQcDCDAgBgNVHSAEGTAXMAgGBmeBDAEE # AjALBglghkgBhv1sBwEwHwYDVR0jBBgwFoAUuhbZbU2FL3MpdpovdYxqII+eyG8w # HQYDVR0OBBYEFKW27xPn783QZKHVVqllMaPe1eNJMFoGA1UdHwRTMFEwT6BNoEuG # SWh0dHA6Ly9jcmwzLmRpZ2ljZXJ0LmNvbS9EaWdpQ2VydFRydXN0ZWRHNFJTQTQw # OTZTSEEyNTZUaW1lU3RhbXBpbmdDQS5jcmwwgZAGCCsGAQUFBwEBBIGDMIGAMCQG # CCsGAQUFBzABhhhodHRwOi8vb2NzcC5kaWdpY2VydC5jb20wWAYIKwYBBQUHMAKG # TGh0dHA6Ly9jYWNlcnRzLmRpZ2ljZXJ0LmNvbS9EaWdpQ2VydFRydXN0ZWRHNFJT # QTQwOTZTSEEyNTZUaW1lU3RhbXBpbmdDQS5jcnQwDQYJKoZIhvcNAQELBQADggIB # AIEa1t6gqbWYF7xwjU+KPGic2CX/yyzkzepdIpLsjCICqbjPgKjZ5+PF7SaCinEv # GN1Ott5s1+FgnCvt7T1IjrhrunxdvcJhN2hJd6PrkKoS1yeF844ektrCQDifXcig # LiV4JZ0qBXqEKZi2V3mP2yZWK7Dzp703DNiYdk9WuVLCtp04qYHnbUFcjGnRuSvE # xnvPnPp44pMadqJpddNQ5EQSviANnqlE0PjlSXcIWiHFtM+YlRpUurm8wWkZus8W # 8oM3NG6wQSbd3lqXTzON1I13fXVFoaVYJmoDRd7ZULVQjK9WvUzF4UbFKNOt50MA # cN7MmJ4ZiQPq1JE3701S88lgIcRWR+3aEUuMMsOI5ljitts++V+wQtaP4xeR0arA # VeOGv6wnLEHQmjNKqDbUuXKWfpd5OEhfysLcPTLfddY2Z1qJ+Panx+VPNTwAvb6c # Kmx5AdzaROY63jg7B145WPR8czFVoIARyxQMfq68/qTreWWqaNYiyjvrmoI1VygW # y2nyMpqy0tg6uLFGhmu6F/3Ed2wVbK6rr3M66ElGt9V/zLY4wNjsHPW2obhDLN9O # TH0eaHDAdwrUAuBcYLso/zjlUlrWrBciI0707NMX+1Br/wd3H3GXREHJuEbTbDJ8 # WC9nR2XlG3O2mflrLAZG70Ee8PBf4NvZrZCARK+AEEGKMIIGrjCCBJagAwIBAgIQ # BzY3tyRUfNhHrP0oZipeWzANBgkqhkiG9w0BAQsFADBiMQswCQYDVQQGEwJVUzEV # MBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQLExB3d3cuZGlnaWNlcnQuY29t # MSEwHwYDVQQDExhEaWdpQ2VydCBUcnVzdGVkIFJvb3QgRzQwHhcNMjIwMzIzMDAw # MDAwWhcNMzcwMzIyMjM1OTU5WjBjMQswCQYDVQQGEwJVUzEXMBUGA1UEChMORGln # aUNlcnQsIEluYy4xOzA5BgNVBAMTMkRpZ2lDZXJ0IFRydXN0ZWQgRzQgUlNBNDA5 # NiBTSEEyNTYgVGltZVN0YW1waW5nIENBMIICIjANBgkqhkiG9w0BAQEFAAOCAg8A # MIICCgKCAgEAxoY1BkmzwT1ySVFVxyUDxPKRN6mXUaHW0oPRnkyibaCwzIP5WvYR # oUQVQl+kiPNo+n3znIkLf50fng8zH1ATCyZzlm34V6gCff1DtITaEfFzsbPuK4CE # iiIY3+vaPcQXf6sZKz5C3GeO6lE98NZW1OcoLevTsbV15x8GZY2UKdPZ7Gnf2ZCH # RgB720RBidx8ald68Dd5n12sy+iEZLRS8nZH92GDGd1ftFQLIWhuNyG7QKxfst5K # fc71ORJn7w6lY2zkpsUdzTYNXNXmG6jBZHRAp8ByxbpOH7G1WE15/tePc5OsLDni # pUjW8LAxE6lXKZYnLvWHpo9OdhVVJnCYJn+gGkcgQ+NDY4B7dW4nJZCYOjgRs/b2 # nuY7W+yB3iIU2YIqx5K/oN7jPqJz+ucfWmyU8lKVEStYdEAoq3NDzt9KoRxrOMUp # 88qqlnNCaJ+2RrOdOqPVA+C/8KI8ykLcGEh/FDTP0kyr75s9/g64ZCr6dSgkQe1C # vwWcZklSUPRR8zZJTYsg0ixXNXkrqPNFYLwjjVj33GHek/45wPmyMKVM1+mYSlg+ # 0wOI/rOP015LdhJRk8mMDDtbiiKowSYI+RQQEgN9XyO7ZONj4KbhPvbCdLI/Hgl2 # 7KtdRnXiYKNYCQEoAA6EVO7O6V3IXjASvUaetdN2udIOa5kM0jO0zbECAwEAAaOC # AV0wggFZMBIGA1UdEwEB/wQIMAYBAf8CAQAwHQYDVR0OBBYEFLoW2W1NhS9zKXaa # L3WMaiCPnshvMB8GA1UdIwQYMBaAFOzX44LScV1kTN8uZz/nupiuHA9PMA4GA1Ud # DwEB/wQEAwIBhjATBgNVHSUEDDAKBggrBgEFBQcDCDB3BggrBgEFBQcBAQRrMGkw # JAYIKwYBBQUHMAGGGGh0dHA6Ly9vY3NwLmRpZ2ljZXJ0LmNvbTBBBggrBgEFBQcw # AoY1aHR0cDovL2NhY2VydHMuZGlnaWNlcnQuY29tL0RpZ2lDZXJ0VHJ1c3RlZFJv # b3RHNC5jcnQwQwYDVR0fBDwwOjA4oDagNIYyaHR0cDovL2NybDMuZGlnaWNlcnQu # Y29tL0RpZ2lDZXJ0VHJ1c3RlZFJvb3RHNC5jcmwwIAYDVR0gBBkwFzAIBgZngQwB # BAIwCwYJYIZIAYb9bAcBMA0GCSqGSIb3DQEBCwUAA4ICAQB9WY7Ak7ZvmKlEIgF+ # ZtbYIULhsBguEE0TzzBTzr8Y+8dQXeJLKftwig2qKWn8acHPHQfpPmDI2AvlXFvX # bYf6hCAlNDFnzbYSlm/EUExiHQwIgqgWvalWzxVzjQEiJc6VaT9Hd/tydBTX/6tP # iix6q4XNQ1/tYLaqT5Fmniye4Iqs5f2MvGQmh2ySvZ180HAKfO+ovHVPulr3qRCy # Xen/KFSJ8NWKcXZl2szwcqMj+sAngkSumScbqyQeJsG33irr9p6xeZmBo1aGqwpF # yd/EjaDnmPv7pp1yr8THwcFqcdnGE4AJxLafzYeHJLtPo0m5d2aR8XKc6UsCUqc3 # fpNTrDsdCEkPlM05et3/JWOZJyw9P2un8WbDQc1PtkCbISFA0LcTJM3cHXg65J6t # 5TRxktcma+Q4c6umAU+9Pzt4rUyt+8SVe+0KXzM5h0F4ejjpnOHdI/0dKNPH+ejx # mF/7K9h+8kaddSweJywm228Vex4Ziza4k9Tm8heZWcpw8De/mADfIBZPJ/tgZxah # ZrrdVcA6KYawmKAr7ZVBtzrVFZgxtGIJDwq9gdkT/r+k0fNX2bwE+oLeMt8EifAA # zV3C+dAjfwAL5HYCJtnwZXZCpimHCUcr5n8apIUP/JiW9lVUKx+A+sDyDivl1vup # L0QVSucTDh3bNzgaoSv27dZ8/DCCBY0wggR1oAMCAQICEA6bGI750C3n79tQ4ghA # GFowDQYJKoZIhvcNAQEMBQAwZTELMAkGA1UEBhMCVVMxFTATBgNVBAoTDERpZ2lD # ZXJ0IEluYzEZMBcGA1UECxMQd3d3LmRpZ2ljZXJ0LmNvbTEkMCIGA1UEAxMbRGln # aUNlcnQgQXNzdXJlZCBJRCBSb290IENBMB4XDTIyMDgwMTAwMDAwMFoXDTMxMTEw # OTIzNTk1OVowYjELMAkGA1UEBhMCVVMxFTATBgNVBAoTDERpZ2lDZXJ0IEluYzEZ # MBcGA1UECxMQd3d3LmRpZ2ljZXJ0LmNvbTEhMB8GA1UEAxMYRGlnaUNlcnQgVHJ1 # c3RlZCBSb290IEc0MIICIjANBgkqhkiG9w0BAQEFAAOCAg8AMIICCgKCAgEAv+aQ # c2jeu+RdSjwwIjBpM+zCpyUuySE98orYWcLhKac9WKt2ms2uexuEDcQwH/MbpDgW # 61bGl20dq7J58soR0uRf1gU8Ug9SH8aeFaV+vp+pVxZZVXKvaJNwwrK6dZlqczKU # 0RBEEC7fgvMHhOZ0O21x4i0MG+4g1ckgHWMpLc7sXk7Ik/ghYZs06wXGXuxbGrzr # yc/NrDRAX7F6Zu53yEioZldXn1RYjgwrt0+nMNlW7sp7XeOtyU9e5TXnMcvak17c # jo+A2raRmECQecN4x7axxLVqGDgDEI3Y1DekLgV9iPWCPhCRcKtVgkEy19sEcypu # kQF8IUzUvK4bA3VdeGbZOjFEmjNAvwjXWkmkwuapoGfdpCe8oU85tRFYF/ckXEaP # ZPfBaYh2mHY9WV1CdoeJl2l6SPDgohIbZpp0yt5LHucOY67m1O+SkjqePdwA5EUl # ibaaRBkrfsCUtNJhbesz2cXfSwQAzH0clcOP9yGyshG3u3/y1YxwLEFgqrFjGESV # GnZifvaAsPvoZKYz0YkH4b235kOkGLimdwHhD5QMIR2yVCkliWzlDlJRR3S+Jqy2 # QXXeeqxfjT/JvNNBERJb5RBQ6zHFynIWIgnffEx1P2PsIV/EIFFrb7GrhotPwtZF # X50g/KEexcCPorF+CiaZ9eRpL5gdLfXZqbId5RsCAwEAAaOCATowggE2MA8GA1Ud # EwEB/wQFMAMBAf8wHQYDVR0OBBYEFOzX44LScV1kTN8uZz/nupiuHA9PMB8GA1Ud # IwQYMBaAFEXroq/0ksuCMS1Ri6enIZ3zbcgPMA4GA1UdDwEB/wQEAwIBhjB5Bggr # BgEFBQcBAQRtMGswJAYIKwYBBQUHMAGGGGh0dHA6Ly9vY3NwLmRpZ2ljZXJ0LmNv # bTBDBggrBgEFBQcwAoY3aHR0cDovL2NhY2VydHMuZGlnaWNlcnQuY29tL0RpZ2lD # ZXJ0QXNzdXJlZElEUm9vdENBLmNydDBFBgNVHR8EPjA8MDqgOKA2hjRodHRwOi8v # Y3JsMy5kaWdpY2VydC5jb20vRGlnaUNlcnRBc3N1cmVkSURSb290Q0EuY3JsMBEG # A1UdIAQKMAgwBgYEVR0gADANBgkqhkiG9w0BAQwFAAOCAQEAcKC/Q1xV5zhfoKN0 # Gz22Ftf3v1cHvZqsoYcs7IVeqRq7IviHGmlUIu2kiHdtvRoU9BNKei8ttzjv9P+A # ufih9/Jy3iS8UgPITtAq3votVs/59PesMHqai7Je1M/RQ0SbQyHrlnKhSLSZy51P # pwYDE3cnRNTnf+hZqPC/Lwum6fI0POz3A8eHqNJMQBk1RmppVLC4oVaO7KTVPeix # 3P0c2PR3WlxUjG/voVA9/HYJaISfb8rbII01YBwCA8sgsKxYoA5AY8WYIsGyWfVV # a88nq2x2zm8jLfR+cWojayL/ErhULSd+2DrZ8LaHlv1b0VysGMNNn3O3AamfV6pe # KOK5lDGCA3YwggNyAgEBMHcwYzELMAkGA1UEBhMCVVMxFzAVBgNVBAoTDkRpZ2lD # ZXJ0LCBJbmMuMTswOQYDVQQDEzJEaWdpQ2VydCBUcnVzdGVkIEc0IFJTQTQwOTYg # U0hBMjU2IFRpbWVTdGFtcGluZyBDQQIQBUSv85SdCDmmv9s/X+VhFjANBglghkgB # ZQMEAgEFAKCB0TAaBgkqhkiG9w0BCQMxDQYLKoZIhvcNAQkQAQQwHAYJKoZIhvcN # AQkFMQ8XDTI0MDkxNDA3Mzc1MlowKwYLKoZIhvcNAQkQAgwxHDAaMBgwFgQUZvAr # MsLCyQ+CXc6qisnGTxmcz0AwLwYJKoZIhvcNAQkEMSIEIBNKWUham/vupWCgvP7f # hWwci1snyNG85INQtUFmMRp5MDcGCyqGSIb3DQEJEAIvMSgwJjAkMCIEINL25G3t # dCLM0dRAV2hBNm+CitpVmq4zFq9NGprUDHgoMA0GCSqGSIb3DQEBAQUABIICAE5d # c7/HRokcLYRDte35z9ohROgVwtWPNMiAySc5489ZZ0a0l4e7QsYwHDUyPdTxLU5X # FxHQpuoB1M9mu2JjxApd3LtivrudADwzOblD9QtV+Rdkh2U1B1tLVNdyPI9bUnVY # xiiqvmn7ZhkEH+EjeFZEC4XlWqUXhKKib4lEKUoMfC/6iWNIkz47FyH002YNVVl0 # zqb85kyRgt0XRkjE/2TbEfEIGsiwRBrzc5MMqfcGlve5j6cccU/Mv+qC9zZZJnLa # ybE/Zqw+YTLbqoXSRB6J1xRTQzVXf3KkuSzNRz/UO32EzeW94A40PYS8rdiYWTlA # 3cBXfIwqsLLhyRkCft20QGbLYTeDEIgBd37X3Y4y88ebcGgDNE8cvmLqEmNxxqKv # gLzSIIM9MkLVZryKazZD6Y4f+L97RUtvbCHn0f+YFKhTm6vLc4ikzaifPkaFehvk # cNP+2MMyckhjmLF9N6aKjLB8hD6HE7MdzVcGuRujJrUCo+mHlJsOR+pLdMjDDfI+ # LYwt3Aq3CGlMVulg1uKlEATPxWRconSWOTFhLHaT1HuSggP/Kn2V9PG6xfulbXQU # 8UJ5a7nzaihXTwfBkcGOobOikpkV/Lf/6C58osbwxupIcIXzUMLVn4t8sH9Fdhcd # jHaOjsk7XFzvHlt5/+hNRsD8+ehW64geEXBvjdtE # SIG # End signature block |