diff --git a/crypto/src/asn1/Asn1UtcTime.cs b/crypto/src/asn1/Asn1UtcTime.cs
index 05de430c4..478b5c485 100644
--- a/crypto/src/asn1/Asn1UtcTime.cs
+++ b/crypto/src/asn1/Asn1UtcTime.cs
@@ -1,14 +1,13 @@
using System;
using System.Globalization;
using System.IO;
+using System.Text;
using Org.BouncyCastle.Utilities;
namespace Org.BouncyCastle.Asn1
{
- /**
- * UTC time object.
- */
+ /// <summary>UTCTime ASN.1 type</summary>
public class Asn1UtcTime
: Asn1Object
{
@@ -55,210 +54,206 @@ namespace Org.BouncyCastle.Asn1
}
}
- throw new ArgumentException("illegal object in GetInstance: " + Platform.GetTypeName(obj));
+ throw new ArgumentException("illegal object in GetInstance: " + Platform.GetTypeName(obj), nameof(obj));
}
- /**
- * return a UTC Time from a tagged object.
- *
- * @param taggedObject the tagged object holding the object we want
- * @param declaredExplicit true if the object is meant to be explicitly tagged false otherwise.
- * @exception ArgumentException if the tagged object cannot be converted.
- */
public static Asn1UtcTime GetInstance(Asn1TaggedObject taggedObject, bool declaredExplicit)
{
return (Asn1UtcTime)Meta.Instance.GetContextInstance(taggedObject, declaredExplicit);
}
- private readonly string time;
+ private readonly string m_timeString;
+ private readonly DateTime m_dateTime;
+ private readonly bool m_dateTimeLocked;
+ private readonly int m_twoDigitYearMax;
- /**
- * The correct format for this is YYMMDDHHMMSSZ (it used to be that seconds were
- * never encoded. When you're creating one of these objects from scratch, that's
- * what you want to use, otherwise we'll try to deal with whatever Gets read from
- * the input stream... (this is why the input format is different from the GetTime()
- * method output).
- * <p>
- * @param time the time string.</p>
- */
- public Asn1UtcTime(string time)
- {
- if (time == null)
- throw new ArgumentNullException("time");
+ public Asn1UtcTime(string timeString)
+ {
+ if (timeString == null)
+ throw new ArgumentNullException(nameof(timeString));
- this.time = time;
+ m_timeString = timeString;
try
{
- ToDateTime();
- }
- catch (FormatException e)
+ m_dateTime = FromString(timeString, out m_twoDigitYearMax);
+ m_dateTimeLocked = false;
+ }
+ catch (FormatException e)
{
throw new ArgumentException("invalid date string: " + e.Message);
}
- }
+ }
- /**
- * base constructor from a DateTime object
- */
- public Asn1UtcTime(DateTime time)
- {
- this.time = time.ToUniversalTime().ToString("yyMMddHHmmss", CultureInfo.InvariantCulture) + "Z";
+ [Obsolete("Use `Asn1UtcTime(DateTime, int)' instead")]
+ public Asn1UtcTime(DateTime dateTime)
+ {
+ DateTime utc = dateTime.ToUniversalTime();
+ dateTime = new DateTime(utc.Year, utc.Month, utc.Day, utc.Hour, utc.Minute, utc.Second, DateTimeKind.Utc);
+
+ m_dateTime = dateTime;
+ m_dateTimeLocked = true;
+ m_timeString = ToStringCanonical(dateTime, out m_twoDigitYearMax);
}
- internal Asn1UtcTime(byte[] contents)
+ public Asn1UtcTime(DateTime dateTime, int twoDigitYearMax)
{
- //
- // explicitly convert to characters
- //
- this.time = Strings.FromAsciiByteArray(contents);
+ DateTime utc = dateTime.ToUniversalTime();
+ dateTime = new DateTime(utc.Year, utc.Month, utc.Day, utc.Hour, utc.Minute, utc.Second, DateTimeKind.Utc);
+
+ Validate(dateTime, twoDigitYearMax);
+
+ m_dateTime = dateTime;
+ m_dateTimeLocked = true;
+ m_timeString = ToStringCanonical(dateTime);
+ m_twoDigitYearMax = twoDigitYearMax;
}
- /**
- * return the time as a date based on whatever a 2 digit year will return. For
- * standardised processing use ToAdjustedDateTime().
- *
- * @return the resulting date
- * @exception ParseException if the date string cannot be parsed.
- */
- public DateTime ToDateTime()
+ internal Asn1UtcTime(byte[] contents)
+ // NOTE: Non-ASCII characters will produce '?' characters, which will fail DateTime parsing
+ : this(Encoding.ASCII.GetString(contents))
{
- return ParseDateString(TimeString, @"yyMMddHHmmss'GMT'zzz");
}
- /**
- * return the time as an adjusted date
- * in the range of 1950 - 2049.
- *
- * @return a date in the range of 1950 to 2049.
- * @exception ParseException if the date string cannot be parsed.
- */
- public DateTime ToAdjustedDateTime()
+ public string TimeString => m_timeString;
+
+ public DateTime ToDateTime()
{
- return ParseDateString(AdjustedTimeString, @"yyyyMMddHHmmss'GMT'zzz");
+ return m_dateTime;
}
- private DateTime ParseDateString(string dateStr, string formatStr)
- {
- DateTime dt = DateTime.ParseExact(
- dateStr,
- formatStr,
- DateTimeFormatInfo.InvariantInfo);
+ public DateTime ToDateTime(int twoDigitYearMax)
+ {
+ if (InRange(m_dateTime, twoDigitYearMax))
+ return m_dateTime;
- return dt.ToUniversalTime();
- }
+ if (m_dateTimeLocked)
+ throw new InvalidOperationException();
- /**
- * return the time - always in the form of
- * YYMMDDhhmmssGMT(+hh:mm|-hh:mm).
- * <p>
- * Normally in a certificate we would expect "Z" rather than "GMT",
- * however adding the "GMT" means we can just use:
- * <pre>
- * dateF = new SimpleDateFormat("yyMMddHHmmssz");
- * </pre>
- * To read in the time and Get a date which is compatible with our local
- * time zone.</p>
- * <p>
- * <b>Note:</b> In some cases, due to the local date processing, this
- * may lead to unexpected results. If you want to stick the normal
- * convention of 1950 to 2049 use the GetAdjustedTime() method.</p>
- */
- public string TimeString
+ int twoDigitYear = m_dateTime.Year % 100;
+ int twoDigitYearCutoff = twoDigitYearMax % 100;
+
+ int diff = twoDigitYear - twoDigitYearCutoff;
+ int newYear = twoDigitYearMax + diff;
+ if (diff > 0)
+ {
+ newYear -= 100;
+ }
+
+ return m_dateTime.AddYears(newYear - m_dateTime.Year);
+ }
+
+ public DateTime ToDateTime(Calendar calendar)
{
- get
- {
- //
- // standardise the format.
- //
- if (time.IndexOf('-') < 0 && time.IndexOf('+') < 0)
- {
- if (time.Length == 11)
- {
- return time.Substring(0, 10) + "00GMT+00:00";
- }
- else
- {
- return time.Substring(0, 12) + "GMT+00:00";
- }
- }
- else
- {
- int index = time.IndexOf('-');
- if (index < 0)
- {
- index = time.IndexOf('+');
- }
- string d = time;
-
- if (index == time.Length - 3)
- {
- d += "00";
- }
-
- if (index == 10)
- {
- return d.Substring(0, 10) + "00GMT" + d.Substring(10, 3) + ":" + d.Substring(13, 2);
- }
- else
- {
- return d.Substring(0, 12) + "GMT" + d.Substring(12, 3) + ":" + d.Substring(15, 2);
- }
- }
- }
+ return ToDateTime(calendar.TwoDigitYearMax);
}
- /// <summary>
- /// Return a time string as an adjusted date with a 4 digit year.
- /// This goes in the range of 1950 - 2049.
- /// </summary>
- public string AdjustedTimeString
- {
- get
- {
- string d = TimeString;
- string c = d[0] < '5' ? "20" : "19";
+ /// <summary>Return an adjusted date in the range of 1950 - 2049.</summary>
+ [Obsolete("Use 'ToDateTime(2049)' instead")]
+ public DateTime ToAdjustedDateTime()
+ {
+ return ToDateTime(2049);
+ }
- return c + d;
- }
- }
+ public int TwoDigitYearMax => m_twoDigitYearMax;
- internal byte[] GetOctets()
+ internal byte[] GetContents(int encoding)
{
- return Strings.ToAsciiByteArray(time);
+ if (encoding == Asn1OutputStream.EncodingDer && m_timeString.Length != 13)
+ {
+ string canonical = ToStringCanonical(m_dateTime);
+ return Encoding.ASCII.GetBytes(canonical);
+ }
+
+ return Encoding.ASCII.GetBytes(m_timeString);
}
internal override IAsn1Encoding GetEncoding(int encoding)
{
- return new PrimitiveEncoding(Asn1Tags.Universal, Asn1Tags.UtcTime, GetOctets());
+ return new PrimitiveEncoding(Asn1Tags.Universal, Asn1Tags.UtcTime, GetContents(encoding));
}
internal override IAsn1Encoding GetEncodingImplicit(int encoding, int tagClass, int tagNo)
{
- return new PrimitiveEncoding(tagClass, tagNo, GetOctets());
+ return new PrimitiveEncoding(tagClass, tagNo, GetContents(encoding));
}
protected override bool Asn1Equals(Asn1Object asn1Object)
- {
+ {
if (!(asn1Object is Asn1UtcTime that))
return false;
- return this.time == that.time;
+ // TODO Performance
+ return Arrays.AreEqual(
+ this.GetContents(Asn1OutputStream.EncodingDer),
+ that.GetContents(Asn1OutputStream.EncodingDer));
}
- protected override int Asn1GetHashCode()
- {
- return time.GetHashCode();
+ protected override int Asn1GetHashCode()
+ {
+ // TODO Performance
+ return Arrays.GetHashCode(
+ this.GetContents(Asn1OutputStream.EncodingDer));
}
- public override string ToString()
- {
- return time;
- }
+ public override string ToString()
+ {
+ return m_timeString;
+ }
internal static Asn1UtcTime CreatePrimitive(byte[] contents)
{
return new Asn1UtcTime(contents);
}
+
+ private static DateTime FromString(string s, out int twoDigitYearMax)
+ {
+ var provider = DateTimeFormatInfo.InvariantInfo;
+ twoDigitYearMax = provider.Calendar.TwoDigitYearMax;
+
+ switch (s.Length)
+ {
+ case 11:
+ return DateTime.ParseExact(s, @"yyMMddHHmm\Z", provider,
+ DateTimeStyles.AdjustToUniversal | DateTimeStyles.AssumeUniversal);
+ case 13:
+ return DateTime.ParseExact(s, @"yyMMddHHmmss\Z", provider,
+ DateTimeStyles.AdjustToUniversal | DateTimeStyles.AssumeUniversal);
+ case 15:
+ return DateTime.ParseExact(s, @"yyMMddHHmmzzz", provider,
+ DateTimeStyles.AdjustToUniversal);
+ case 17:
+ return DateTime.ParseExact(s, @"yyMMddHHmmsszzz", provider,
+ DateTimeStyles.AdjustToUniversal);
+ default:
+ throw new FormatException();
+ }
+ }
+
+ private static bool InRange(DateTime dateTime, int twoDigitYearMax)
+ {
+ return (uint)(twoDigitYearMax - dateTime.Year) < 100;
+ }
+
+ private static string ToStringCanonical(DateTime dateTime, out int twoDigitYearMax)
+ {
+ var provider = DateTimeFormatInfo.InvariantInfo;
+ twoDigitYearMax = provider.Calendar.TwoDigitYearMax;
+
+ Validate(dateTime, twoDigitYearMax);
+
+ return dateTime.ToString(@"yyMMddHHmmss\Z", provider);
+ }
+
+ private static string ToStringCanonical(DateTime dateTime)
+ {
+ return dateTime.ToString(@"yyMMddHHmmss\Z", DateTimeFormatInfo.InvariantInfo);
+ }
+
+ private static void Validate(DateTime dateTime, int twoDigitYearMax)
+ {
+ if (!InRange(dateTime, twoDigitYearMax))
+ throw new ArgumentOutOfRangeException(nameof(dateTime));
+ }
}
}
diff --git a/crypto/src/asn1/DerUTCTime.cs b/crypto/src/asn1/DerUTCTime.cs
index 089285367..33e502c67 100644
--- a/crypto/src/asn1/DerUTCTime.cs
+++ b/crypto/src/asn1/DerUTCTime.cs
@@ -5,21 +5,36 @@ namespace Org.BouncyCastle.Asn1
public class DerUtcTime
: Asn1UtcTime
{
- public DerUtcTime(string time)
- : base(time)
+ public DerUtcTime(string timeString)
+ : base(timeString)
{
}
- public DerUtcTime(DateTime time)
- : base(time)
+ [Obsolete("Use `DerUtcTime(DateTime, int)' instead")]
+ public DerUtcTime(DateTime dateTime)
+ : base(dateTime)
{
}
- internal DerUtcTime(byte[] contents)
+ public DerUtcTime(DateTime dateTime, int twoDigitYearMax)
+ : base(dateTime, twoDigitYearMax)
+ {
+ }
+
+ internal DerUtcTime(byte[] contents)
: base(contents)
{
}
- // TODO: create proper DER encoding.
+ internal override IAsn1Encoding GetEncoding(int encoding)
+ {
+ return new PrimitiveEncoding(Asn1Tags.Universal, Asn1Tags.UtcTime,
+ GetContents(Asn1OutputStream.EncodingDer));
+ }
+
+ internal override IAsn1Encoding GetEncodingImplicit(int encoding, int tagClass, int tagNo)
+ {
+ return new PrimitiveEncoding(tagClass, tagNo, GetContents(Asn1OutputStream.EncodingDer));
+ }
}
}
diff --git a/crypto/src/asn1/cms/Time.cs b/crypto/src/asn1/cms/Time.cs
index 67c73285b..f054e3809 100644
--- a/crypto/src/asn1/cms/Time.cs
+++ b/crypto/src/asn1/cms/Time.cs
@@ -8,24 +8,41 @@ namespace Org.BouncyCastle.Asn1.Cms
public class Time
: Asn1Encodable, IAsn1Choice
{
- private readonly Asn1Object time;
+ public static Time GetInstance(object obj)
+ {
+ if (obj == null)
+ return null;
+ if (obj is Time time)
+ return time;
+ if (obj is Asn1UtcTime utcTime)
+ return new Time(utcTime);
+ if (obj is Asn1GeneralizedTime generalizedTime)
+ return new Time(generalizedTime);
+
+ throw new ArgumentException("unknown object in factory: " + Platform.GetTypeName(obj), nameof(obj));
+ }
- public static Time GetInstance(
- Asn1TaggedObject obj,
- bool explicitly)
+ public static Time GetInstance(Asn1TaggedObject taggedObject, bool declaredExplicit)
{
- return GetInstance(obj.GetObject());
+ return GetInstance(taggedObject.GetObject());
}
- public Time(
- Asn1Object time)
+ private readonly Asn1Object m_timeObject;
+
+ public Time(Asn1GeneralizedTime generalizedTime)
+ {
+ this.m_timeObject = generalizedTime ?? throw new ArgumentNullException(nameof(generalizedTime));
+ }
+
+ public Time(Asn1UtcTime utcTime)
{
- if (time == null)
- throw new ArgumentNullException("time");
- if (!(time is Asn1UtcTime) && !(time is Asn1GeneralizedTime))
- throw new ArgumentException("unknown object passed to Time");
+ if (utcTime == null)
+ throw new ArgumentNullException(nameof(utcTime));
- this.time = time;
+ // Validate utcTime is in the appropriate year range
+ utcTime.ToDateTime(2049);
+
+ this.m_timeObject = utcTime;
}
/**
@@ -35,61 +52,36 @@ namespace Org.BouncyCastle.Asn1.Cms
*/
public Time(DateTime date)
{
- DateTime d = date.ToUniversalTime();
+ DateTime utc = date.ToUniversalTime();
- if (d.Year < 1950 || d.Year > 2049)
+ if (utc.Year < 1950 || utc.Year > 2049)
{
- time = new DerGeneralizedTime(d);
+ m_timeObject = new DerGeneralizedTime(utc);
}
else
{
- time = new DerUtcTime(d);
+ m_timeObject = new DerUtcTime(utc, 2049);
}
}
- public static Time GetInstance(object obj)
- {
- if (obj == null)
- return null;
- if (obj is Time time)
- return time;
- if (obj is Asn1UtcTime utcTime)
- return new Time(utcTime);
- if (obj is Asn1GeneralizedTime generalizedTime)
- return new Time(generalizedTime);
-
- throw new ArgumentException("unknown object in factory: " + Platform.GetTypeName(obj), "obj");
- }
-
- public string TimeString
+ public DateTime ToDateTime()
{
- get
- {
- if (time is Asn1UtcTime utcTime)
- return utcTime.AdjustedTimeString;
+ try
+ {
+ if (m_timeObject is Asn1UtcTime utcTime)
+ return utcTime.ToDateTime(2049);
- return ((Asn1GeneralizedTime)time).GetTime();
- }
+ return ((Asn1GeneralizedTime)m_timeObject).ToDateTime();
+ }
+ catch (FormatException e)
+ {
+ // this should never happen
+ throw new InvalidOperationException("invalid date string: " + e.Message);
+ }
}
- public DateTime Date
- {
- get
- {
- try
- {
- if (time is Asn1UtcTime utcTime)
- return utcTime.ToAdjustedDateTime();
-
- return ((Asn1GeneralizedTime)time).ToDateTime();
- }
- catch (FormatException e)
- {
- // this should never happen
- throw new InvalidOperationException("invalid date string: " + e.Message);
- }
- }
- }
+ [Obsolete("Use 'ToDateTime' instead")]
+ public DateTime Date => ToDateTime();
/**
* Produce an object suitable for an Asn1OutputStream.
@@ -101,7 +93,15 @@ namespace Org.BouncyCastle.Asn1.Cms
*/
public override Asn1Object ToAsn1Object()
{
- return time;
+ return m_timeObject;
+ }
+
+ public override string ToString()
+ {
+ if (m_timeObject is Asn1UtcTime utcTime)
+ return utcTime.ToDateTime(2049).ToString(@"yyyyMMddHHmmssK", DateTimeFormatInfo.InvariantInfo);
+
+ return ((Asn1GeneralizedTime)m_timeObject).GetTime();
}
}
}
diff --git a/crypto/src/asn1/esf/CrlIdentifier.cs b/crypto/src/asn1/esf/CrlIdentifier.cs
index 44c99170c..4a2480b4b 100644
--- a/crypto/src/asn1/esf/CrlIdentifier.cs
+++ b/crypto/src/asn1/esf/CrlIdentifier.cs
@@ -20,36 +20,38 @@ namespace Org.BouncyCastle.Asn1.Esf
public class CrlIdentifier
: Asn1Encodable
{
- private readonly X509Name crlIssuer;
+ private readonly X509Name crlIssuer;
private readonly Asn1UtcTime crlIssuedTime;
- private readonly DerInteger crlNumber;
+ private readonly DerInteger crlNumber;
- public static CrlIdentifier GetInstance(
- object obj)
+ public static CrlIdentifier GetInstance(object obj)
{
- if (obj == null || obj is CrlIdentifier)
- return (CrlIdentifier) obj;
+ if (obj == null)
+ return null;
- if (obj is Asn1Sequence)
- return new CrlIdentifier((Asn1Sequence) obj);
+ if (obj is CrlIdentifier crlIdentifier)
+ return crlIdentifier;
- throw new ArgumentException(
- "Unknown object in 'CrlIdentifier' factory: "
- + Platform.GetTypeName(obj),
- "obj");
+ if (obj is Asn1Sequence asn1Sequence)
+ return new CrlIdentifier(asn1Sequence);
+
+ throw new ArgumentException("Unknown object in 'CrlIdentifier' factory: " + Platform.GetTypeName(obj),
+ nameof(obj));
}
- private CrlIdentifier(
- Asn1Sequence seq)
+ private CrlIdentifier(Asn1Sequence seq)
{
if (seq == null)
- throw new ArgumentNullException("seq");
+ throw new ArgumentNullException(nameof(seq));
if (seq.Count < 2 || seq.Count > 3)
- throw new ArgumentException("Bad sequence size: " + seq.Count, "seq");
+ throw new ArgumentException("Bad sequence size: " + seq.Count, nameof(seq));
this.crlIssuer = X509Name.GetInstance(seq[0]);
this.crlIssuedTime = Asn1UtcTime.GetInstance(seq[1]);
+ // Validate crlIssuedTime is in the appropriate year range
+ crlIssuedTime.ToDateTime(2049);
+
if (seq.Count > 2)
{
this.crlNumber = DerInteger.GetInstance(seq[2]);
@@ -62,7 +64,7 @@ namespace Org.BouncyCastle.Asn1.Esf
}
public CrlIdentifier(X509Name crlIssuer, DateTime crlIssuedTime, BigInteger crlNumber)
- : this(crlIssuer, new Asn1UtcTime(crlIssuedTime), crlNumber)
+ : this(crlIssuer, new Asn1UtcTime(crlIssuedTime, 2049), crlNumber)
{
}
@@ -75,6 +77,11 @@ namespace Org.BouncyCastle.Asn1.Esf
{
if (crlIssuer == null)
throw new ArgumentNullException(nameof(crlIssuer));
+ if (crlIssuedTime == null)
+ throw new ArgumentNullException(nameof(crlIssuedTime));
+
+ // Validate crlIssuedTime is in the appropriate year range
+ crlIssuedTime.ToDateTime(2049);
this.crlIssuer = crlIssuer;
this.crlIssuedTime = crlIssuedTime;
@@ -92,7 +99,7 @@ namespace Org.BouncyCastle.Asn1.Esf
public DateTime CrlIssuedTime
{
- get { return crlIssuedTime.ToAdjustedDateTime(); }
+ get { return crlIssuedTime.ToDateTime(2049); }
}
public BigInteger CrlNumber
diff --git a/crypto/src/asn1/x509/Time.cs b/crypto/src/asn1/x509/Time.cs
index 8260043aa..7f2d43315 100644
--- a/crypto/src/asn1/x509/Time.cs
+++ b/crypto/src/asn1/x509/Time.cs
@@ -8,24 +8,41 @@ namespace Org.BouncyCastle.Asn1.X509
public class Time
: Asn1Encodable, IAsn1Choice
{
- private readonly Asn1Object time;
+ public static Time GetInstance(object obj)
+ {
+ if (obj == null)
+ return null;
+ if (obj is Time time)
+ return time;
+ if (obj is Asn1UtcTime utcTime)
+ return new Time(utcTime);
+ if (obj is Asn1GeneralizedTime generalizedTime)
+ return new Time(generalizedTime);
+
+ throw new ArgumentException("unknown object in factory: " + Platform.GetTypeName(obj), nameof(obj));
+ }
- public static Time GetInstance(
- Asn1TaggedObject obj,
- bool explicitly)
+ public static Time GetInstance(Asn1TaggedObject taggedObject, bool declaredExplicit)
{
- return GetInstance(obj.GetObject());
+ return GetInstance(taggedObject.GetObject());
}
- public Time(
- Asn1Object time)
+ private readonly Asn1Object m_timeObject;
+
+ public Time(Asn1GeneralizedTime generalizedTime)
{
- if (time == null)
- throw new ArgumentNullException("time");
- if (!(time is Asn1UtcTime) && !(time is Asn1GeneralizedTime))
- throw new ArgumentException("unknown object passed to Time");
+ this.m_timeObject = generalizedTime ?? throw new ArgumentNullException(nameof(generalizedTime));
+ }
- this.time = time;
+ public Time(Asn1UtcTime utcTime)
+ {
+ if (utcTime == null)
+ throw new ArgumentNullException(nameof(utcTime));
+
+ // Validate utcTime is in the appropriate year range
+ utcTime.ToDateTime(2049);
+
+ this.m_timeObject = utcTime;
}
/**
@@ -35,40 +52,18 @@ namespace Org.BouncyCastle.Asn1.X509
*/
public Time(DateTime date)
{
- DateTime d = date.ToUniversalTime();
+ DateTime utc = date.ToUniversalTime();
- if (d.Year < 1950 || d.Year > 2049)
+ if (utc.Year < 1950 || utc.Year > 2049)
{
- time = new DerGeneralizedTime(d);
+ m_timeObject = new DerGeneralizedTime(utc);
}
else
{
- time = new DerUtcTime(d);
+ m_timeObject = new DerUtcTime(utc, 2049);
}
}
- public static Time GetInstance(object obj)
- {
- if (obj == null)
- return null;
- if (obj is Time time)
- return time;
- if (obj is Asn1UtcTime utcTime)
- return new Time(utcTime);
- if (obj is Asn1GeneralizedTime generalizedTime)
- return new Time(generalizedTime);
-
- throw new ArgumentException("unknown object in factory: " + Platform.GetTypeName(obj), "obj");
- }
-
- public string GetTime()
- {
- if (time is Asn1UtcTime utcTime)
- return utcTime.AdjustedTimeString;
-
- return ((Asn1GeneralizedTime)time).GetTime();
- }
-
/// <summary>
/// Return our time as DateTime.
/// </summary>
@@ -77,10 +72,10 @@ namespace Org.BouncyCastle.Asn1.X509
{
try
{
- if (time is Asn1UtcTime utcTime)
- return utcTime.ToAdjustedDateTime();
+ if (m_timeObject is Asn1UtcTime utcTime)
+ return utcTime.ToDateTime(2049);
- return ((Asn1GeneralizedTime)time).ToDateTime();
+ return ((Asn1GeneralizedTime)m_timeObject).ToDateTime();
}
catch (FormatException e)
{
@@ -99,12 +94,15 @@ namespace Org.BouncyCastle.Asn1.X509
*/
public override Asn1Object ToAsn1Object()
{
- return time;
+ return m_timeObject;
}
public override string ToString()
{
- return GetTime();
+ if (m_timeObject is Asn1UtcTime utcTime)
+ return utcTime.ToDateTime(2049).ToString(@"yyyyMMddHHmmssK", DateTimeFormatInfo.InvariantInfo);
+
+ return ((Asn1GeneralizedTime)m_timeObject).GetTime();
}
}
}
diff --git a/crypto/src/cms/SignerInformation.cs b/crypto/src/cms/SignerInformation.cs
index 99d300121..6454e6d3d 100644
--- a/crypto/src/cms/SignerInformation.cs
+++ b/crypto/src/cms/SignerInformation.cs
@@ -651,7 +651,7 @@ namespace Org.BouncyCastle.Cms
Asn1.Cms.Time signingTime = GetSigningTime();
if (signingTime != null)
{
- cert.CheckValidity(signingTime.Date);
+ cert.CheckValidity(signingTime.ToDateTime());
}
return DoVerify(cert.GetPublicKey());
diff --git a/crypto/src/x509/X509Certificate.cs b/crypto/src/x509/X509Certificate.cs
index 627903e1f..510f95b01 100644
--- a/crypto/src/x509/X509Certificate.cs
+++ b/crypto/src/x509/X509Certificate.cs
@@ -205,9 +205,9 @@ namespace Org.BouncyCastle.X509
DateTime time)
{
if (time.CompareTo(NotAfter) > 0)
- throw new CertificateExpiredException("certificate expired on " + c.EndDate.GetTime());
+ throw new CertificateExpiredException("certificate expired on " + c.EndDate);
if (time.CompareTo(NotBefore) < 0)
- throw new CertificateNotYetValidException("certificate not valid until " + c.StartDate.GetTime());
+ throw new CertificateNotYetValidException("certificate not valid until " + c.StartDate);
}
/// <summary>
|