1
/* ****************************************************************************
3 * Copyright (c) Microsoft Corporation. All rights reserved.
5 * This software is subject to the Microsoft Public License (Ms-PL).
6 * A copy of the license can be found in the license.htm file included
7 * in this distribution.
9 * You must not remove this notice, or any other, from this software.
11 * ***************************************************************************/
13 namespace System
.Web
.Mvc
{
15 using System
.Security
.Cryptography
;
18 internal sealed class AntiForgeryData
{
20 private const string AntiForgeryTokenFieldName
= "__RequestVerificationToken";
22 private const int TokenLength
= 128 / 8;
23 private static RNGCryptoServiceProvider _prng
= new RNGCryptoServiceProvider();
26 private string _value
;
28 public AntiForgeryData() {
32 public AntiForgeryData(AntiForgeryData token
) {
34 throw new ArgumentNullException("token");
37 CreationDate
= token
.CreationDate
;
42 public DateTime CreationDate
{
49 return _salt
?? String
.Empty
;
58 return _value
?? String
.Empty
;
65 private static string Base64EncodeForCookieName(string s
) {
66 byte[] rawBytes
= Encoding
.UTF8
.GetBytes(s
);
67 string base64String
= Convert
.ToBase64String(rawBytes
);
69 // replace base64-specific characters with characters that are safe for a cookie name
70 return base64String
.Replace('+', '.').Replace('/', '-').Replace('=', '_');
73 private static string GenerateRandomTokenString() {
74 byte[] tokenBytes
= new byte[TokenLength
];
75 _prng
.GetBytes(tokenBytes
);
77 string token
= Convert
.ToBase64String(tokenBytes
);
81 // If the app path is provided, we're generating a cookie name rather than a field name, and the cookie names should
82 // be unique so that a development server cookie and an IIS cookie - both running on localhost - don't stomp on
84 internal static string GetAntiForgeryTokenName(string appPath
) {
85 if (String
.IsNullOrEmpty(appPath
)) {
86 return AntiForgeryTokenFieldName
;
89 return AntiForgeryTokenFieldName
+ "_" + Base64EncodeForCookieName(appPath
);
93 public static AntiForgeryData
NewToken() {
94 string tokenString
= GenerateRandomTokenString();
95 return new AntiForgeryData() {
96 CreationDate
= DateTime
.Now
,